mirror of
https://github.com/Auxilor/EcoMobs.git
synced 2025-12-19 23:19:17 +00:00
Compare commits
75 Commits
| Author | SHA1 | Date | |
|---|---|---|---|
|
|
041ec1c79e | ||
|
|
f0b09c035e | ||
|
|
4c6ac852aa | ||
|
|
9772081d7b | ||
|
|
cea2d96819 | ||
|
|
9dbba3f751 | ||
|
|
9cecb33b04 | ||
|
|
7b60749b88 | ||
|
|
e0d03cc8ed | ||
|
|
80109fc061 | ||
|
|
c1fc918757 | ||
|
|
955a378b98 | ||
|
|
a1875933c8 | ||
|
|
cf3c302513 | ||
|
|
2acdc4a74e | ||
|
|
0e2cdb71cb | ||
|
|
f1c26763e0 | ||
|
|
b75b83aebf | ||
|
|
ea2b14fbec | ||
|
|
0747a0a3d4 | ||
|
|
260aec8ba4 | ||
|
|
77985e5a23 | ||
|
|
201ec4161b | ||
|
|
468b0b4292 | ||
|
|
203bec560e | ||
|
|
a2c8b73dbc | ||
|
|
31ccdf2589 | ||
|
|
7ea1f8938b | ||
|
|
436e833213 | ||
|
|
60b4c1c246 | ||
|
|
c5f5032e17 | ||
|
|
310ace62b3 | ||
|
|
0af79cfc27 | ||
|
|
a107d78937 | ||
|
|
d8c229d4fa | ||
|
|
406601a193 | ||
|
|
fb9fdacb9f | ||
|
|
45bbc668dc | ||
|
|
b5f222976b | ||
|
|
10d297e0da | ||
|
|
76df0fd2ef | ||
|
|
56b76f70c6 | ||
|
|
30e0ed02a4 | ||
|
|
2795fa8220 | ||
|
|
cbeff28dbf | ||
|
|
38dd7ea604 | ||
|
|
af72bfbbb6 | ||
|
|
de675b49be | ||
|
|
3df4cfaae7 | ||
|
|
32ac455720 | ||
|
|
89a7d37d37 | ||
|
|
04eff9d3f3 | ||
|
|
c3c96a6892 | ||
|
|
d135922dc1 | ||
|
|
1569d12b44 | ||
|
|
aea6e5c2f1 | ||
|
|
d837311ae2 | ||
|
|
c66b914104 | ||
|
|
1f73b9acf7 | ||
|
|
cafb41567f | ||
|
|
8f912abf31 | ||
|
|
2fe8c9197d | ||
|
|
46eccfc345 | ||
|
|
7804cebd53 | ||
|
|
1918a46678 | ||
|
|
99de824b04 | ||
|
|
b18eb3942a | ||
|
|
7434bbb38e | ||
|
|
7bf88ed09a | ||
|
|
d8f54cb9f6 | ||
|
|
3bc5ed6f6a | ||
|
|
ab759afe56 | ||
|
|
3ae961c9c5 | ||
|
|
b6754c6d5c | ||
|
|
846b03d8bc |
17
README.md
17
README.md
@@ -1,14 +1,14 @@
|
||||
<h1 align="center">
|
||||
<br>
|
||||
<img src="https://i.imgur.com/I74yjwu.png" alt="EcoBosses logo" width="256">
|
||||
<img src="https://i.imgur.com/A2qieC3.png" alt="EcoBosses logo" width="256">
|
||||
<br>
|
||||
</h1>
|
||||
|
||||
<h4 align="center">Source code for EcoBosses, a premium spigot plugin.</h4>
|
||||
|
||||
<p align="center">
|
||||
<a href="https://www.spigotmc.org/resources/ecobosses.79573/">
|
||||
<img alt="spigot" src="https://img.shields.io/badge/spigot-ecobosses-blue?style=for-the-badge"/>
|
||||
<a href="https://polymart.org/resource/1-16-1-17-ecobosses.525">
|
||||
<img alt="spigot" src="https://img.shields.io/badge/polymart-ecobosses-blue?style=for-the-badge"/>
|
||||
</a>
|
||||
<a href="https://bstats.org/plugin/bukkit/EcoBosses" alt="bstats servers">
|
||||
<img src="https://img.shields.io/bstats/servers/10635?color=blue&style=for-the-badge"/>
|
||||
@@ -29,3 +29,14 @@
|
||||
|
||||
## License
|
||||
*Click here to read [the entire license](https://github.com/Auxilor/EcoBosses/blob/master/LICENSE.md).*
|
||||
|
||||
<h1 align="center">
|
||||
<br>
|
||||
<a href="http://gamersupps.gg/discount/Auxilor?afmc=Auxilor" target="_blank">
|
||||
<img src="https://i.imgur.com/uFDpBAC.png" alt="supps banner">
|
||||
</a>
|
||||
<a href="https://dedimc.promo/Auxilor" target="_blank">
|
||||
<img src="https://i.imgur.com/zdDLhFA.png" alt="dedimc banner">
|
||||
</a>
|
||||
<br>
|
||||
</h1>
|
||||
|
||||
15
build.gradle
15
build.gradle
@@ -6,7 +6,7 @@ plugins {
|
||||
}
|
||||
|
||||
dependencies {
|
||||
implementation project(":eco-core").getSubprojects()
|
||||
implementation project(":eco-core:core-plugin")
|
||||
}
|
||||
|
||||
allprojects {
|
||||
@@ -39,6 +39,7 @@ allprojects {
|
||||
maven { url 'https://maven.sk89q.com/repo/' }
|
||||
maven { url 'https://github.com/factions-site/repo/raw/public/' }
|
||||
maven { url 'https://repo.extendedclip.com/content/repositories/placeholderapi/' }
|
||||
maven { url 'https://mvn.lumine.io/repository/maven-public/' }
|
||||
}
|
||||
|
||||
jar {
|
||||
@@ -46,7 +47,7 @@ allprojects {
|
||||
}
|
||||
|
||||
dependencies {
|
||||
compileOnly 'com.willfp:eco:6.0.0'
|
||||
compileOnly 'com.willfp:eco:6.9.0'
|
||||
|
||||
compileOnly 'org.jetbrains:annotations:19.0.0'
|
||||
|
||||
@@ -85,7 +86,15 @@ shadowJar {
|
||||
}
|
||||
|
||||
jar {
|
||||
archiveFileName = findProperty("plugin-name") + " v" + findProperty("version") + " " + "unshaded" + ".jar"
|
||||
archiveFileName = findProperty("plugin-name") + " v" + findProperty("version") + ".jar"
|
||||
}
|
||||
|
||||
publishing {
|
||||
publications {
|
||||
maven(MavenPublication) {
|
||||
from(components.java)
|
||||
}
|
||||
}
|
||||
}
|
||||
|
||||
group = 'com.willfp'
|
||||
|
||||
@@ -1,9 +0,0 @@
|
||||
group 'com.willfp'
|
||||
version rootProject.version
|
||||
|
||||
subprojects {
|
||||
dependencies {
|
||||
compileOnly project(':eco-core:core-proxy')
|
||||
compileOnly project(':eco-core:core-plugin')
|
||||
}
|
||||
}
|
||||
@@ -1,6 +0,0 @@
|
||||
group 'com.willfp'
|
||||
version rootProject.version
|
||||
|
||||
dependencies {
|
||||
compileOnly 'org.spigotmc:spigot:1.16.1-R0.1-SNAPSHOT'
|
||||
}
|
||||
@@ -1,22 +0,0 @@
|
||||
package com.willfp.ecobosses.proxy.v1_16_R1;
|
||||
|
||||
import com.willfp.ecobosses.proxy.proxies.CustomEntitySpawnerProxy;
|
||||
import com.willfp.ecobosses.proxy.proxies.CustomIllusionerProxy;
|
||||
import com.willfp.ecobosses.proxy.util.CustomEntity;
|
||||
import org.bukkit.Location;
|
||||
import org.bukkit.entity.LivingEntity;
|
||||
import org.jetbrains.annotations.NotNull;
|
||||
import org.jetbrains.annotations.Nullable;
|
||||
|
||||
@SuppressWarnings("unchecked")
|
||||
public class CustomEntitySpawner implements CustomEntitySpawnerProxy {
|
||||
@Override
|
||||
public <T extends LivingEntity> @Nullable T spawnCustomEntity(final Class<? extends CustomEntity<? extends LivingEntity>> entityClass,
|
||||
@NotNull final Location location) {
|
||||
if (entityClass.equals(CustomIllusionerProxy.class)) {
|
||||
return (T) CustomIllusioner.spawn(location);
|
||||
}
|
||||
|
||||
return null;
|
||||
}
|
||||
}
|
||||
@@ -1,62 +0,0 @@
|
||||
package com.willfp.ecobosses.proxy.v1_16_R1;
|
||||
|
||||
import com.willfp.ecobosses.proxy.proxies.CustomIllusionerProxy;
|
||||
import net.minecraft.server.v1_16_R1.EntityHuman;
|
||||
import net.minecraft.server.v1_16_R1.EntityIllagerIllusioner;
|
||||
import net.minecraft.server.v1_16_R1.EntityIllagerWizard;
|
||||
import net.minecraft.server.v1_16_R1.EntityInsentient;
|
||||
import net.minecraft.server.v1_16_R1.EntityIronGolem;
|
||||
import net.minecraft.server.v1_16_R1.EntityRaider;
|
||||
import net.minecraft.server.v1_16_R1.EntityTypes;
|
||||
import net.minecraft.server.v1_16_R1.EntityVillagerAbstract;
|
||||
import net.minecraft.server.v1_16_R1.PathfinderGoalBowShoot;
|
||||
import net.minecraft.server.v1_16_R1.PathfinderGoalFloat;
|
||||
import net.minecraft.server.v1_16_R1.PathfinderGoalHurtByTarget;
|
||||
import net.minecraft.server.v1_16_R1.PathfinderGoalLookAtPlayer;
|
||||
import net.minecraft.server.v1_16_R1.PathfinderGoalMeleeAttack;
|
||||
import net.minecraft.server.v1_16_R1.PathfinderGoalNearestAttackableTarget;
|
||||
import net.minecraft.server.v1_16_R1.PathfinderGoalRandomStroll;
|
||||
import org.bukkit.Location;
|
||||
import org.bukkit.craftbukkit.v1_16_R1.CraftWorld;
|
||||
import org.bukkit.entity.Illusioner;
|
||||
import org.jetbrains.annotations.NotNull;
|
||||
|
||||
public class CustomIllusioner extends EntityIllagerIllusioner implements CustomIllusionerProxy {
|
||||
/**
|
||||
* Instantiate a new custom illusioner entity.
|
||||
*
|
||||
* @param location The location to spawn it at.
|
||||
*/
|
||||
public CustomIllusioner(@NotNull final Location location) {
|
||||
super(EntityTypes.ILLUSIONER, ((CraftWorld) location.getWorld()).getHandle());
|
||||
|
||||
this.setPosition(location.getX(), location.getY(), location.getZ());
|
||||
|
||||
this.goalSelector.a(0, new PathfinderGoalFloat(this));
|
||||
this.goalSelector.a(1, new EntityIllagerWizard.b());
|
||||
this.goalSelector.a(2, new PathfinderGoalMeleeAttack(this, 1.0D, false));
|
||||
this.goalSelector.a(2, new PathfinderGoalBowShoot<>(this, 1.0D, 20, 15.0F));
|
||||
this.goalSelector.a(8, new PathfinderGoalRandomStroll(this, 0.6D));
|
||||
this.goalSelector.a(0, new PathfinderGoalFloat(this));
|
||||
this.goalSelector.a(6, new PathfinderGoalBowShoot<>(this, 0.5D, 20, 15.0F));
|
||||
this.goalSelector.a(8, new PathfinderGoalRandomStroll(this, 0.6D));
|
||||
this.goalSelector.a(9, new PathfinderGoalLookAtPlayer(this, EntityHuman.class, 3.0F, 1.0F));
|
||||
this.goalSelector.a(10, new PathfinderGoalLookAtPlayer(this, EntityInsentient.class, 8.0F));
|
||||
this.targetSelector.a(1, (new PathfinderGoalHurtByTarget(this, new Class[]{EntityRaider.class})).a(new Class[0]));
|
||||
this.targetSelector.a(2, (new PathfinderGoalNearestAttackableTarget<>(this, EntityHuman.class, true)).a(300));
|
||||
this.targetSelector.a(3, (new PathfinderGoalNearestAttackableTarget<>(this, EntityVillagerAbstract.class, false)).a(300));
|
||||
this.targetSelector.a(3, (new PathfinderGoalNearestAttackableTarget<>(this, EntityIronGolem.class, false)).a(300));
|
||||
}
|
||||
|
||||
/**
|
||||
* Spawn illusioner.
|
||||
*
|
||||
* @param location The location.
|
||||
* @return The illusioner.
|
||||
*/
|
||||
public static Illusioner spawn(@NotNull final Location location) {
|
||||
CustomIllusioner illusioner = new CustomIllusioner(location);
|
||||
((CraftWorld) location.getWorld()).getHandle().addEntity(illusioner);
|
||||
return (Illusioner) illusioner.getBukkitEntity();
|
||||
}
|
||||
}
|
||||
@@ -1,6 +0,0 @@
|
||||
group 'com.willfp'
|
||||
version rootProject.version
|
||||
|
||||
dependencies {
|
||||
compileOnly 'org.spigotmc:spigot:1.16.3-R0.1-SNAPSHOT'
|
||||
}
|
||||
@@ -1,22 +0,0 @@
|
||||
package com.willfp.ecobosses.proxy.v1_16_R2;
|
||||
|
||||
import com.willfp.ecobosses.proxy.proxies.CustomEntitySpawnerProxy;
|
||||
import com.willfp.ecobosses.proxy.proxies.CustomIllusionerProxy;
|
||||
import com.willfp.ecobosses.proxy.util.CustomEntity;
|
||||
import org.bukkit.Location;
|
||||
import org.bukkit.entity.LivingEntity;
|
||||
import org.jetbrains.annotations.NotNull;
|
||||
import org.jetbrains.annotations.Nullable;
|
||||
|
||||
@SuppressWarnings("unchecked")
|
||||
public class CustomEntitySpawner implements CustomEntitySpawnerProxy {
|
||||
@Override
|
||||
public <T extends LivingEntity> @Nullable T spawnCustomEntity(final Class<? extends CustomEntity<? extends LivingEntity>> entityClass,
|
||||
@NotNull final Location location) {
|
||||
if (entityClass.equals(CustomIllusionerProxy.class)) {
|
||||
return (T) CustomIllusioner.spawn(location);
|
||||
}
|
||||
|
||||
return null;
|
||||
}
|
||||
}
|
||||
@@ -1,62 +0,0 @@
|
||||
package com.willfp.ecobosses.proxy.v1_16_R2;
|
||||
|
||||
import com.willfp.ecobosses.proxy.proxies.CustomIllusionerProxy;
|
||||
import net.minecraft.server.v1_16_R2.EntityHuman;
|
||||
import net.minecraft.server.v1_16_R2.EntityIllagerIllusioner;
|
||||
import net.minecraft.server.v1_16_R2.EntityIllagerWizard;
|
||||
import net.minecraft.server.v1_16_R2.EntityInsentient;
|
||||
import net.minecraft.server.v1_16_R2.EntityIronGolem;
|
||||
import net.minecraft.server.v1_16_R2.EntityRaider;
|
||||
import net.minecraft.server.v1_16_R2.EntityTypes;
|
||||
import net.minecraft.server.v1_16_R2.EntityVillagerAbstract;
|
||||
import net.minecraft.server.v1_16_R2.PathfinderGoalBowShoot;
|
||||
import net.minecraft.server.v1_16_R2.PathfinderGoalFloat;
|
||||
import net.minecraft.server.v1_16_R2.PathfinderGoalHurtByTarget;
|
||||
import net.minecraft.server.v1_16_R2.PathfinderGoalLookAtPlayer;
|
||||
import net.minecraft.server.v1_16_R2.PathfinderGoalMeleeAttack;
|
||||
import net.minecraft.server.v1_16_R2.PathfinderGoalNearestAttackableTarget;
|
||||
import net.minecraft.server.v1_16_R2.PathfinderGoalRandomStroll;
|
||||
import org.bukkit.Location;
|
||||
import org.bukkit.craftbukkit.v1_16_R2.CraftWorld;
|
||||
import org.bukkit.entity.Illusioner;
|
||||
import org.jetbrains.annotations.NotNull;
|
||||
|
||||
public class CustomIllusioner extends EntityIllagerIllusioner implements CustomIllusionerProxy {
|
||||
/**
|
||||
* Instantiate a new custom illusioner entity.
|
||||
*
|
||||
* @param location The location to spawn it at.
|
||||
*/
|
||||
public CustomIllusioner(@NotNull final Location location) {
|
||||
super(EntityTypes.ILLUSIONER, ((CraftWorld) location.getWorld()).getHandle());
|
||||
|
||||
this.setPosition(location.getX(), location.getY(), location.getZ());
|
||||
|
||||
this.goalSelector.a(0, new PathfinderGoalFloat(this));
|
||||
this.goalSelector.a(1, new EntityIllagerWizard.b());
|
||||
this.goalSelector.a(2, new PathfinderGoalMeleeAttack(this, 1.0D, false));
|
||||
this.goalSelector.a(2, new PathfinderGoalBowShoot<>(this, 1.0D, 20, 15.0F));
|
||||
this.goalSelector.a(8, new PathfinderGoalRandomStroll(this, 0.6D));
|
||||
this.goalSelector.a(0, new PathfinderGoalFloat(this));
|
||||
this.goalSelector.a(6, new PathfinderGoalBowShoot<>(this, 0.5D, 20, 15.0F));
|
||||
this.goalSelector.a(8, new PathfinderGoalRandomStroll(this, 0.6D));
|
||||
this.goalSelector.a(9, new PathfinderGoalLookAtPlayer(this, EntityHuman.class, 3.0F, 1.0F));
|
||||
this.goalSelector.a(10, new PathfinderGoalLookAtPlayer(this, EntityInsentient.class, 8.0F));
|
||||
this.targetSelector.a(1, (new PathfinderGoalHurtByTarget(this, new Class[]{EntityRaider.class})).a(new Class[0]));
|
||||
this.targetSelector.a(2, (new PathfinderGoalNearestAttackableTarget<>(this, EntityHuman.class, true)).a(300));
|
||||
this.targetSelector.a(3, (new PathfinderGoalNearestAttackableTarget<>(this, EntityVillagerAbstract.class, false)).a(300));
|
||||
this.targetSelector.a(3, (new PathfinderGoalNearestAttackableTarget<>(this, EntityIronGolem.class, false)).a(300));
|
||||
}
|
||||
|
||||
/**
|
||||
* Spawn illusioner.
|
||||
*
|
||||
* @param location The location.
|
||||
* @return The illusioner.
|
||||
*/
|
||||
public static Illusioner spawn(@NotNull final Location location) {
|
||||
CustomIllusioner illusioner = new CustomIllusioner(location);
|
||||
((CraftWorld) location.getWorld()).getHandle().addEntity(illusioner);
|
||||
return (Illusioner) illusioner.getBukkitEntity();
|
||||
}
|
||||
}
|
||||
@@ -1,6 +0,0 @@
|
||||
group 'com.willfp'
|
||||
version rootProject.version
|
||||
|
||||
dependencies {
|
||||
compileOnly 'org.spigotmc:spigot:1.16.4-R0.1-SNAPSHOT'
|
||||
}
|
||||
@@ -1,22 +0,0 @@
|
||||
package com.willfp.ecobosses.proxy.v1_16_R3;
|
||||
|
||||
import com.willfp.ecobosses.proxy.proxies.CustomEntitySpawnerProxy;
|
||||
import com.willfp.ecobosses.proxy.proxies.CustomIllusionerProxy;
|
||||
import com.willfp.ecobosses.proxy.util.CustomEntity;
|
||||
import org.bukkit.Location;
|
||||
import org.bukkit.entity.LivingEntity;
|
||||
import org.jetbrains.annotations.NotNull;
|
||||
import org.jetbrains.annotations.Nullable;
|
||||
|
||||
@SuppressWarnings("unchecked")
|
||||
public class CustomEntitySpawner implements CustomEntitySpawnerProxy {
|
||||
@Override
|
||||
public <T extends LivingEntity> @Nullable T spawnCustomEntity(final Class<? extends CustomEntity<? extends LivingEntity>> entityClass,
|
||||
@NotNull final Location location) {
|
||||
if (entityClass.equals(CustomIllusionerProxy.class)) {
|
||||
return (T) CustomIllusioner.spawn(location);
|
||||
}
|
||||
|
||||
return null;
|
||||
}
|
||||
}
|
||||
@@ -1,62 +0,0 @@
|
||||
package com.willfp.ecobosses.proxy.v1_16_R3;
|
||||
|
||||
import com.willfp.ecobosses.proxy.proxies.CustomIllusionerProxy;
|
||||
import net.minecraft.server.v1_16_R3.EntityHuman;
|
||||
import net.minecraft.server.v1_16_R3.EntityIllagerIllusioner;
|
||||
import net.minecraft.server.v1_16_R3.EntityIllagerWizard;
|
||||
import net.minecraft.server.v1_16_R3.EntityInsentient;
|
||||
import net.minecraft.server.v1_16_R3.EntityIronGolem;
|
||||
import net.minecraft.server.v1_16_R3.EntityRaider;
|
||||
import net.minecraft.server.v1_16_R3.EntityTypes;
|
||||
import net.minecraft.server.v1_16_R3.EntityVillagerAbstract;
|
||||
import net.minecraft.server.v1_16_R3.PathfinderGoalBowShoot;
|
||||
import net.minecraft.server.v1_16_R3.PathfinderGoalFloat;
|
||||
import net.minecraft.server.v1_16_R3.PathfinderGoalHurtByTarget;
|
||||
import net.minecraft.server.v1_16_R3.PathfinderGoalLookAtPlayer;
|
||||
import net.minecraft.server.v1_16_R3.PathfinderGoalMeleeAttack;
|
||||
import net.minecraft.server.v1_16_R3.PathfinderGoalNearestAttackableTarget;
|
||||
import net.minecraft.server.v1_16_R3.PathfinderGoalRandomStroll;
|
||||
import org.bukkit.Location;
|
||||
import org.bukkit.craftbukkit.v1_16_R3.CraftWorld;
|
||||
import org.bukkit.entity.Illusioner;
|
||||
import org.jetbrains.annotations.NotNull;
|
||||
|
||||
public class CustomIllusioner extends EntityIllagerIllusioner implements CustomIllusionerProxy {
|
||||
/**
|
||||
* Instantiate a new custom illusioner entity.
|
||||
*
|
||||
* @param location The location to spawn it at.
|
||||
*/
|
||||
public CustomIllusioner(@NotNull final Location location) {
|
||||
super(EntityTypes.ILLUSIONER, ((CraftWorld) location.getWorld()).getHandle());
|
||||
|
||||
this.setPosition(location.getX(), location.getY(), location.getZ());
|
||||
|
||||
this.goalSelector.a(0, new PathfinderGoalFloat(this));
|
||||
this.goalSelector.a(1, new EntityIllagerWizard.b());
|
||||
this.goalSelector.a(2, new PathfinderGoalMeleeAttack(this, 1.0D, false));
|
||||
this.goalSelector.a(2, new PathfinderGoalBowShoot<>(this, 1.0D, 20, 15.0F));
|
||||
this.goalSelector.a(8, new PathfinderGoalRandomStroll(this, 0.6D));
|
||||
this.goalSelector.a(0, new PathfinderGoalFloat(this));
|
||||
this.goalSelector.a(6, new PathfinderGoalBowShoot<>(this, 0.5D, 20, 15.0F));
|
||||
this.goalSelector.a(8, new PathfinderGoalRandomStroll(this, 0.6D));
|
||||
this.goalSelector.a(9, new PathfinderGoalLookAtPlayer(this, EntityHuman.class, 3.0F, 1.0F));
|
||||
this.goalSelector.a(10, new PathfinderGoalLookAtPlayer(this, EntityInsentient.class, 8.0F));
|
||||
this.targetSelector.a(1, (new PathfinderGoalHurtByTarget(this, new Class[]{EntityRaider.class})).a(new Class[0]));
|
||||
this.targetSelector.a(2, (new PathfinderGoalNearestAttackableTarget<>(this, EntityHuman.class, true)).a(300));
|
||||
this.targetSelector.a(3, (new PathfinderGoalNearestAttackableTarget<>(this, EntityVillagerAbstract.class, false)).a(300));
|
||||
this.targetSelector.a(3, (new PathfinderGoalNearestAttackableTarget<>(this, EntityIronGolem.class, false)).a(300));
|
||||
}
|
||||
|
||||
/**
|
||||
* Spawn illusioner.
|
||||
*
|
||||
* @param location The location.
|
||||
* @return The illusioner.
|
||||
*/
|
||||
public static Illusioner spawn(@NotNull final Location location) {
|
||||
CustomIllusioner illusioner = new CustomIllusioner(location);
|
||||
((CraftWorld) location.getWorld()).getHandle().addEntity(illusioner);
|
||||
return (Illusioner) illusioner.getBukkitEntity();
|
||||
}
|
||||
}
|
||||
@@ -1,6 +0,0 @@
|
||||
group 'com.willfp'
|
||||
version rootProject.version
|
||||
|
||||
dependencies {
|
||||
compileOnly 'org.spigotmc:spigot:1.17-R0.1-SNAPSHOT'
|
||||
}
|
||||
@@ -1,22 +0,0 @@
|
||||
package com.willfp.ecobosses.proxy.v1_17_R1;
|
||||
|
||||
import com.willfp.ecobosses.proxy.proxies.CustomEntitySpawnerProxy;
|
||||
import com.willfp.ecobosses.proxy.proxies.CustomIllusionerProxy;
|
||||
import com.willfp.ecobosses.proxy.util.CustomEntity;
|
||||
import org.bukkit.Location;
|
||||
import org.bukkit.entity.LivingEntity;
|
||||
import org.jetbrains.annotations.NotNull;
|
||||
import org.jetbrains.annotations.Nullable;
|
||||
|
||||
@SuppressWarnings("unchecked")
|
||||
public class CustomEntitySpawner implements CustomEntitySpawnerProxy {
|
||||
@Override
|
||||
public <T extends LivingEntity> @Nullable T spawnCustomEntity(final Class<? extends CustomEntity<? extends LivingEntity>> entityClass,
|
||||
@NotNull final Location location) {
|
||||
if (entityClass.equals(CustomIllusionerProxy.class)) {
|
||||
return (T) CustomIllusioner.spawn(location);
|
||||
}
|
||||
|
||||
return null;
|
||||
}
|
||||
}
|
||||
@@ -1,62 +0,0 @@
|
||||
package com.willfp.ecobosses.proxy.v1_17_R1;
|
||||
|
||||
import com.willfp.ecobosses.proxy.proxies.CustomIllusionerProxy;
|
||||
import net.minecraft.world.entity.EntityInsentient;
|
||||
import net.minecraft.world.entity.EntityTypes;
|
||||
import net.minecraft.world.entity.ai.goal.PathfinderGoalBowShoot;
|
||||
import net.minecraft.world.entity.ai.goal.PathfinderGoalFloat;
|
||||
import net.minecraft.world.entity.ai.goal.PathfinderGoalLookAtPlayer;
|
||||
import net.minecraft.world.entity.ai.goal.PathfinderGoalMeleeAttack;
|
||||
import net.minecraft.world.entity.ai.goal.PathfinderGoalRandomStroll;
|
||||
import net.minecraft.world.entity.ai.goal.target.PathfinderGoalHurtByTarget;
|
||||
import net.minecraft.world.entity.ai.goal.target.PathfinderGoalNearestAttackableTarget;
|
||||
import net.minecraft.world.entity.animal.EntityIronGolem;
|
||||
import net.minecraft.world.entity.monster.EntityIllagerIllusioner;
|
||||
import net.minecraft.world.entity.monster.EntityIllagerWizard;
|
||||
import net.minecraft.world.entity.npc.EntityVillagerAbstract;
|
||||
import net.minecraft.world.entity.player.EntityHuman;
|
||||
import net.minecraft.world.entity.raid.EntityRaider;
|
||||
import org.bukkit.Location;
|
||||
import org.bukkit.craftbukkit.v1_17_R1.CraftWorld;
|
||||
import org.bukkit.entity.Illusioner;
|
||||
import org.jetbrains.annotations.NotNull;
|
||||
|
||||
public class CustomIllusioner extends EntityIllagerIllusioner implements CustomIllusionerProxy {
|
||||
/**
|
||||
* Instantiate a new custom illusioner entity.
|
||||
*
|
||||
* @param location The location to spawn it at.
|
||||
*/
|
||||
public CustomIllusioner(@NotNull final Location location) {
|
||||
super(EntityTypes.O, ((CraftWorld) location.getWorld()).getHandle());
|
||||
|
||||
this.setPosition(location.getX(), location.getY(), location.getZ());
|
||||
|
||||
this.bO.a(0, new PathfinderGoalFloat(this));
|
||||
this.bO.a(1, new EntityIllagerWizard.b());
|
||||
this.bO.a(2, new PathfinderGoalMeleeAttack(this, 1.0D, false));
|
||||
this.bO.a(2, new PathfinderGoalBowShoot<>(this, 1.0D, 20, 15.0F));
|
||||
this.bO.a(8, new PathfinderGoalRandomStroll(this, 0.6D));
|
||||
this.bO.a(0, new PathfinderGoalFloat(this));
|
||||
this.bO.a(6, new PathfinderGoalBowShoot<>(this, 0.5D, 20, 15.0F));
|
||||
this.bO.a(8, new PathfinderGoalRandomStroll(this, 0.6D));
|
||||
this.bO.a(9, new PathfinderGoalLookAtPlayer(this, EntityHuman.class, 3.0F, 1.0F));
|
||||
this.bO.a(10, new PathfinderGoalLookAtPlayer(this, EntityInsentient.class, 8.0F));
|
||||
this.bP.a(1, (new PathfinderGoalHurtByTarget(this, new Class[]{EntityRaider.class})).a(new Class[0]));
|
||||
this.bP.a(2, (new PathfinderGoalNearestAttackableTarget<>(this, EntityHuman.class, true)).a(300));
|
||||
this.bP.a(3, (new PathfinderGoalNearestAttackableTarget<>(this, EntityVillagerAbstract.class, false)).a(300));
|
||||
this.bP.a(3, (new PathfinderGoalNearestAttackableTarget<>(this, EntityIronGolem.class, false)).a(300));
|
||||
}
|
||||
|
||||
/**
|
||||
* Spawn illusioner.
|
||||
*
|
||||
* @param location The location.
|
||||
* @return The illusioner.
|
||||
*/
|
||||
public static Illusioner spawn(@NotNull final Location location) {
|
||||
CustomIllusioner illusioner = new CustomIllusioner(location);
|
||||
((CraftWorld) location.getWorld()).getHandle().addEntity(illusioner);
|
||||
return (Illusioner) illusioner.getBukkitEntity();
|
||||
}
|
||||
}
|
||||
@@ -2,8 +2,9 @@ group 'com.willfp'
|
||||
version rootProject.version
|
||||
|
||||
dependencies {
|
||||
compileOnly project(":eco-core:core-proxy")
|
||||
compileOnly 'org.spigotmc:spigot-api:1.16.4-R0.1-SNAPSHOT'
|
||||
compileOnly 'org.spigotmc:spigot-api:1.17.1-R0.1-SNAPSHOT'
|
||||
compileOnly 'commons-io:commons-io:2.8.0'
|
||||
compileOnly 'com.destroystokyo.paper:paper-api:1.16.3-R0.1-SNAPSHOT'
|
||||
compileOnly 'com.github.lokka30:LevelledMobs:3.1.4'
|
||||
compileOnly 'io.lumine.xikage:MythicMobs:4.9.1'
|
||||
compileOnly 'net.kyori:adventure-api:4.9.1'
|
||||
}
|
||||
@@ -2,6 +2,7 @@ package com.willfp.ecobosses;
|
||||
|
||||
import com.willfp.eco.core.EcoPlugin;
|
||||
import com.willfp.eco.core.command.impl.PluginCommand;
|
||||
import com.willfp.eco.core.integrations.IntegrationLoader;
|
||||
import com.willfp.ecobosses.bosses.listeners.AttackListeners;
|
||||
import com.willfp.ecobosses.bosses.listeners.AutoSpawnTimer;
|
||||
import com.willfp.ecobosses.bosses.listeners.DeathListeners;
|
||||
@@ -9,6 +10,8 @@ import com.willfp.ecobosses.bosses.listeners.PassiveListeners;
|
||||
import com.willfp.ecobosses.bosses.listeners.SpawnListeners;
|
||||
import com.willfp.ecobosses.bosses.util.BossUtils;
|
||||
import com.willfp.ecobosses.commands.CommandEcobosses;
|
||||
import com.willfp.ecobosses.integrations.levelledmobs.LevelledMobsListener;
|
||||
import com.willfp.ecobosses.util.DiscoverRecipeListener;
|
||||
import lombok.Getter;
|
||||
import org.bukkit.event.Listener;
|
||||
|
||||
@@ -27,10 +30,15 @@ public class EcoBossesPlugin extends EcoPlugin {
|
||||
* Internal constructor called by bukkit on plugin load.
|
||||
*/
|
||||
public EcoBossesPlugin() {
|
||||
super(86576, 10635, "com.willfp.ecobosses.proxy", "&9");
|
||||
super(525, 10635, "com.willfp.ecobosses.proxy", "&9");
|
||||
instance = this;
|
||||
}
|
||||
|
||||
@Override
|
||||
public String getMinimumEcoVersion() {
|
||||
return "6.9.0";
|
||||
}
|
||||
|
||||
@Override
|
||||
protected void handleDisable() {
|
||||
BossUtils.killAllBosses();
|
||||
@@ -43,17 +51,25 @@ public class EcoBossesPlugin extends EcoPlugin {
|
||||
|
||||
@Override
|
||||
protected List<PluginCommand> loadPluginCommands() {
|
||||
return Arrays.asList(
|
||||
return List.of(
|
||||
new CommandEcobosses(this)
|
||||
);
|
||||
}
|
||||
|
||||
@Override
|
||||
protected List<IntegrationLoader> loadIntegrationLoaders() {
|
||||
return Arrays.asList(
|
||||
new IntegrationLoader("LevelledMobs", () -> this.getEventManager().registerListener(new LevelledMobsListener()))
|
||||
);
|
||||
}
|
||||
|
||||
@Override
|
||||
protected List<Listener> loadListeners() {
|
||||
return Arrays.asList(
|
||||
new AttackListeners(this),
|
||||
new DeathListeners(this),
|
||||
new SpawnListeners(this),
|
||||
new DiscoverRecipeListener(this),
|
||||
new PassiveListeners(this)
|
||||
);
|
||||
}
|
||||
|
||||
@@ -4,13 +4,23 @@ import com.google.common.collect.ImmutableMap;
|
||||
import com.willfp.eco.core.EcoPlugin;
|
||||
import com.willfp.eco.core.PluginDependent;
|
||||
import com.willfp.eco.core.config.interfaces.Config;
|
||||
import com.willfp.eco.core.integrations.placeholder.PlaceholderEntry;
|
||||
import com.willfp.eco.core.items.Items;
|
||||
import com.willfp.eco.core.items.builder.ItemBuilder;
|
||||
import com.willfp.eco.core.items.builder.ItemStackBuilder;
|
||||
import com.willfp.eco.core.recipe.Recipes;
|
||||
import com.willfp.eco.core.requirement.Requirement;
|
||||
import com.willfp.eco.core.requirement.Requirements;
|
||||
import com.willfp.eco.core.tuples.Pair;
|
||||
import com.willfp.eco.util.NumberUtils;
|
||||
import com.willfp.eco.util.StringUtils;
|
||||
import com.willfp.ecobosses.bosses.effects.Effect;
|
||||
import com.willfp.ecobosses.bosses.effects.Effects;
|
||||
import com.willfp.ecobosses.bosses.util.bosstype.BossEntityUtils;
|
||||
import com.willfp.ecobosses.bosses.util.bosstype.BossType;
|
||||
import com.willfp.ecobosses.bosses.util.obj.ArgumentedEffectName;
|
||||
import com.willfp.ecobosses.bosses.util.obj.BossbarProperties;
|
||||
import com.willfp.ecobosses.bosses.util.obj.EquipmentPiece;
|
||||
import com.willfp.ecobosses.bosses.util.obj.ExperienceOptions;
|
||||
import com.willfp.ecobosses.bosses.util.obj.ImmunityOptions;
|
||||
import com.willfp.ecobosses.bosses.util.obj.OptionedSound;
|
||||
@@ -18,28 +28,33 @@ import com.willfp.ecobosses.bosses.util.obj.SpawnTotem;
|
||||
import com.willfp.ecobosses.bosses.util.obj.TargetMode;
|
||||
import lombok.AccessLevel;
|
||||
import lombok.Getter;
|
||||
import lombok.Setter;
|
||||
import net.kyori.adventure.bossbar.BossBar;
|
||||
import org.bukkit.Bukkit;
|
||||
import org.bukkit.Location;
|
||||
import org.bukkit.Material;
|
||||
import org.bukkit.Sound;
|
||||
import org.bukkit.World;
|
||||
import org.bukkit.boss.BarColor;
|
||||
import org.bukkit.boss.BarStyle;
|
||||
import org.bukkit.configuration.InvalidConfigurationException;
|
||||
import org.bukkit.configuration.file.YamlConfiguration;
|
||||
import org.bukkit.enchantments.Enchantment;
|
||||
import org.bukkit.entity.LivingEntity;
|
||||
import org.bukkit.entity.Player;
|
||||
import org.bukkit.event.entity.EntityDamageEvent;
|
||||
import org.bukkit.inventory.EquipmentSlot;
|
||||
import org.bukkit.inventory.ItemFlag;
|
||||
import org.bukkit.inventory.ItemStack;
|
||||
import org.bukkit.persistence.PersistentDataType;
|
||||
import org.jetbrains.annotations.NotNull;
|
||||
import org.jetbrains.annotations.Nullable;
|
||||
|
||||
import java.math.BigDecimal;
|
||||
import java.math.RoundingMode;
|
||||
import java.util.ArrayList;
|
||||
import java.util.Arrays;
|
||||
import java.util.Base64;
|
||||
import java.util.HashMap;
|
||||
import java.util.List;
|
||||
import java.util.Map;
|
||||
import java.util.Objects;
|
||||
import java.util.UUID;
|
||||
import java.util.stream.Collectors;
|
||||
|
||||
public class EcoBoss extends PluginDependent<EcoPlugin> {
|
||||
@@ -108,6 +123,11 @@ public class EcoBoss extends PluginDependent<EcoPlugin> {
|
||||
@Getter
|
||||
private final int attackDamage;
|
||||
|
||||
/**
|
||||
* Age state.
|
||||
*/
|
||||
@Getter
|
||||
private final boolean baby;
|
||||
|
||||
/**
|
||||
* The follow range.
|
||||
@@ -130,8 +150,7 @@ public class EcoBoss extends PluginDependent<EcoPlugin> {
|
||||
/**
|
||||
* The drops.
|
||||
*/
|
||||
@Getter
|
||||
private final Map<ItemStack, Double> drops;
|
||||
private final List<String> drops;
|
||||
|
||||
/**
|
||||
* The exp to drop.
|
||||
@@ -169,6 +188,12 @@ public class EcoBoss extends PluginDependent<EcoPlugin> {
|
||||
@Getter
|
||||
private final List<OptionedSound> summonSounds;
|
||||
|
||||
/**
|
||||
* Despawn sounds.
|
||||
*/
|
||||
@Getter
|
||||
private final List<OptionedSound> despawnSounds;
|
||||
|
||||
/**
|
||||
* Spawn messages.
|
||||
*/
|
||||
@@ -181,6 +206,12 @@ public class EcoBoss extends PluginDependent<EcoPlugin> {
|
||||
@Getter
|
||||
private final List<String> deathMessages;
|
||||
|
||||
/**
|
||||
* Despawn messages.
|
||||
*/
|
||||
@Getter
|
||||
private final List<String> despawnMessages;
|
||||
|
||||
/**
|
||||
* Nearby players radius.
|
||||
*/
|
||||
@@ -205,6 +236,12 @@ public class EcoBoss extends PluginDependent<EcoPlugin> {
|
||||
@Getter
|
||||
private final Map<EntityDamageEvent.DamageCause, Double> incomingMultipliers;
|
||||
|
||||
/**
|
||||
* Boss glowing effect.
|
||||
*/
|
||||
@Getter
|
||||
private final boolean isGlowing;
|
||||
|
||||
/**
|
||||
* The currently living bosses of this type.
|
||||
*/
|
||||
@@ -213,7 +250,7 @@ public class EcoBoss extends PluginDependent<EcoPlugin> {
|
||||
/**
|
||||
* The effect names and arguments.
|
||||
*/
|
||||
private final Map<String, List<String>> effectNames;
|
||||
private final List<ArgumentedEffectName> effectNames;
|
||||
|
||||
/**
|
||||
* The target distance.
|
||||
@@ -239,12 +276,44 @@ public class EcoBoss extends PluginDependent<EcoPlugin> {
|
||||
@Getter
|
||||
private final int autoSpawnInterval;
|
||||
|
||||
@Getter
|
||||
@Setter
|
||||
private int timeUntilSpawn;
|
||||
|
||||
/**
|
||||
* The time to live.
|
||||
*/
|
||||
@Getter
|
||||
private final int timeToLive;
|
||||
|
||||
/**
|
||||
* Locations that the boss can auto spawn at.
|
||||
*/
|
||||
@Getter
|
||||
private final List<Location> autoSpawnLocations;
|
||||
|
||||
/**
|
||||
* The boss spawn egg.
|
||||
*/
|
||||
@Getter
|
||||
private final ItemStack spawnEgg;
|
||||
|
||||
/**
|
||||
* All the requirements needed in order to spawn the boss.
|
||||
*/
|
||||
private final Map<Requirement, List<String>> requirements = new HashMap<>();
|
||||
|
||||
/**
|
||||
* Cached players to see if they meet requirements.
|
||||
*/
|
||||
private final Map<UUID, Boolean> cachedRequirements = new HashMap<>();
|
||||
|
||||
/**
|
||||
* The equipment for the boss.
|
||||
*/
|
||||
@Getter
|
||||
private final Map<EquipmentSlot, EquipmentPiece> equipment = new HashMap<>();
|
||||
|
||||
/**
|
||||
* Create a new Boss.
|
||||
*
|
||||
@@ -259,6 +328,8 @@ public class EcoBoss extends PluginDependent<EcoPlugin> {
|
||||
this.config = config;
|
||||
this.name = name;
|
||||
this.livingBosses = new HashMap<>();
|
||||
this.isGlowing = this.getConfig().getBool("glowing");
|
||||
this.baby = this.getConfig().getBool("baby");
|
||||
|
||||
this.displayName = this.getConfig().getString("name");
|
||||
|
||||
@@ -267,9 +338,13 @@ public class EcoBoss extends PluginDependent<EcoPlugin> {
|
||||
|
||||
// Boss Bar
|
||||
this.bossbarEnabled = this.getConfig().getBool("bossbar.enabled");
|
||||
String barStyle = this.getConfig().getString("bossbar.style").toUpperCase();
|
||||
if (barStyle.equalsIgnoreCase("solid")) {
|
||||
barStyle = "PROGRESS";
|
||||
}
|
||||
this.bossbarProperties = new BossbarProperties(
|
||||
BarColor.valueOf(this.getConfig().getString("bossbar.color").toUpperCase()),
|
||||
BarStyle.valueOf(this.getConfig().getString("bossbar.style").toUpperCase())
|
||||
BossBar.Color.valueOf(this.getConfig().getString("bossbar.color").toUpperCase()),
|
||||
BossBar.Overlay.valueOf(barStyle)
|
||||
);
|
||||
|
||||
// Attributes
|
||||
@@ -277,6 +352,61 @@ public class EcoBoss extends PluginDependent<EcoPlugin> {
|
||||
this.maxHealth = this.getConfig().getInt("max-health");
|
||||
this.followRange = this.getConfig().getInt("follow-range");
|
||||
this.movementSpeedMultiplier = this.getConfig().getInt("movement-speed");
|
||||
this.timeToLive = this.getConfig().getInt("time-to-live", -1);
|
||||
|
||||
// Equipment
|
||||
ItemStack helmet = Items.lookup(this.getConfig().getString("gear.helmet.item")).getItem();
|
||||
ItemStack chestplate = Items.lookup(this.getConfig().getString("gear.chestplate.item")).getItem();
|
||||
ItemStack leggings = Items.lookup(this.getConfig().getString("gear.leggings.item")).getItem();
|
||||
ItemStack boots = Items.lookup(this.getConfig().getString("gear.boots.item")).getItem();
|
||||
ItemStack hand = Items.lookup(this.getConfig().getString("gear.hand.item")).getItem();
|
||||
|
||||
if (helmet.getType() != Material.AIR) {
|
||||
this.equipment.put(
|
||||
EquipmentSlot.HEAD,
|
||||
new EquipmentPiece(
|
||||
helmet,
|
||||
this.getConfig().getDouble("gear.helmet.chance")
|
||||
)
|
||||
);
|
||||
}
|
||||
if (chestplate.getType() != Material.AIR) {
|
||||
this.equipment.put(
|
||||
EquipmentSlot.CHEST,
|
||||
new EquipmentPiece(
|
||||
chestplate,
|
||||
this.getConfig().getDouble("gear.chestplate.chance")
|
||||
)
|
||||
);
|
||||
}
|
||||
if (leggings.getType() != Material.AIR) {
|
||||
this.equipment.put(
|
||||
EquipmentSlot.LEGS,
|
||||
new EquipmentPiece(
|
||||
leggings,
|
||||
this.getConfig().getDouble("gear.leggings.chance")
|
||||
)
|
||||
);
|
||||
}
|
||||
if (boots.getType() != Material.AIR) {
|
||||
this.equipment.put(
|
||||
EquipmentSlot.FEET,
|
||||
new EquipmentPiece(
|
||||
boots,
|
||||
this.getConfig().getDouble("gear.boots.chance")
|
||||
)
|
||||
);
|
||||
}
|
||||
if (hand.getType() != Material.AIR) {
|
||||
this.equipment.put(
|
||||
EquipmentSlot.HAND,
|
||||
new EquipmentPiece(
|
||||
hand,
|
||||
this.getConfig().getDouble("gear.hand.chance")
|
||||
)
|
||||
);
|
||||
}
|
||||
|
||||
|
||||
// Spawn Totem
|
||||
this.spawnTotemEnabled = this.getConfig().getBool("spawn-totem.enabled");
|
||||
@@ -288,24 +418,8 @@ public class EcoBoss extends PluginDependent<EcoPlugin> {
|
||||
this.spawnTotemDisabledWorldNames = this.getConfig().getStrings("spawn-totem.world-blacklist").stream().map(String::toLowerCase).collect(Collectors.toList());
|
||||
|
||||
// Rewards
|
||||
this.drops = new HashMap<>();
|
||||
for (String string : this.getConfig().getStrings("rewards.drops")) {
|
||||
YamlConfiguration tempConfig = new YamlConfiguration();
|
||||
double chance = 100;
|
||||
if (string.contains("::")) {
|
||||
String[] split = string.split("::");
|
||||
chance = Double.parseDouble(split[0]);
|
||||
string = split[1];
|
||||
}
|
||||
String tempConfigString = new String(Base64.getDecoder().decode(string));
|
||||
try {
|
||||
tempConfig.loadFromString(tempConfigString);
|
||||
} catch (InvalidConfigurationException e) {
|
||||
e.printStackTrace();
|
||||
}
|
||||
ItemStack itemStack = tempConfig.getItemStack("drop-key");
|
||||
this.drops.put(itemStack, chance);
|
||||
}
|
||||
this.drops = new ArrayList<>();
|
||||
drops.addAll(this.getConfig().getStrings("rewards.drops", false));
|
||||
|
||||
this.experienceOptions = new ExperienceOptions(
|
||||
this.getConfig().getInt("rewards.xp.minimum"),
|
||||
@@ -374,6 +488,16 @@ public class EcoBoss extends PluginDependent<EcoPlugin> {
|
||||
));
|
||||
}
|
||||
|
||||
this.despawnSounds = new ArrayList<>();
|
||||
for (String string : this.getConfig().getStrings("sounds.despawn")) {
|
||||
String[] split = string.split(":");
|
||||
this.despawnSounds.add(new OptionedSound(
|
||||
Sound.valueOf(split[0].toUpperCase()),
|
||||
Float.parseFloat(split[1]) / 16,
|
||||
Float.parseFloat(split[2])
|
||||
));
|
||||
}
|
||||
|
||||
// Messages
|
||||
this.spawnMessages = new ArrayList<>();
|
||||
for (String string : this.getConfig().getStrings("broadcast.spawn")) {
|
||||
@@ -383,6 +507,10 @@ public class EcoBoss extends PluginDependent<EcoPlugin> {
|
||||
for (String string : this.getConfig().getStrings("broadcast.death")) {
|
||||
this.deathMessages.add(StringUtils.format(string));
|
||||
}
|
||||
this.despawnMessages = new ArrayList<>();
|
||||
for (String string : this.getConfig().getStrings("broadcast.despawn")) {
|
||||
this.despawnMessages.add(StringUtils.format(string));
|
||||
}
|
||||
|
||||
// Top Damager Commands
|
||||
this.topDamagerCommands = new HashMap<>();
|
||||
@@ -415,19 +543,24 @@ public class EcoBoss extends PluginDependent<EcoPlugin> {
|
||||
}
|
||||
|
||||
// Effects
|
||||
this.effectNames = new HashMap<>();
|
||||
this.effectNames = new ArrayList<>();
|
||||
for (String string : this.getConfig().getStrings("effects")) {
|
||||
String effectName = string.split(":")[0];
|
||||
List<String> args = Arrays.asList(string.replace(effectName + ":", "").split(":"));
|
||||
this.effectNames.put(effectName, args);
|
||||
List<String> args = new ArrayList<>(Arrays.asList(string.replace(effectName + ":", "").split(":")));
|
||||
if (args.contains("mythicmobs")) {
|
||||
String newArg = "mythicmobs:" + args.get(args.indexOf("mythicmobs")+1);
|
||||
args.set(args.indexOf("mythicmobs"), newArg);
|
||||
args.remove(args.get(args.indexOf(newArg)+1));
|
||||
}
|
||||
this.effectNames.add(new ArgumentedEffectName(effectName, args));
|
||||
}
|
||||
|
||||
new HashMap<>(this.effectNames).forEach((string, args) -> {
|
||||
if (Effects.getEffect(string, args) == null) {
|
||||
this.effectNames.remove(string);
|
||||
Bukkit.getLogger().warning("Invalid effect specified in " + this.name);
|
||||
for (ArgumentedEffectName effectName : new ArrayList<>(this.effectNames)) {
|
||||
if (Effects.getEffect(effectName.name(), effectName.args()) == null) {
|
||||
this.effectNames.remove(effectName);
|
||||
Bukkit.getLogger().warning("Invalid effect " + effectName.name() + " specified in " + this.name);
|
||||
}
|
||||
}
|
||||
});
|
||||
|
||||
// Targeting
|
||||
this.targetDistance = this.getConfig().getDouble("attacks.target.range");
|
||||
@@ -438,6 +571,7 @@ public class EcoBoss extends PluginDependent<EcoPlugin> {
|
||||
|
||||
// Auto Spawn
|
||||
this.autoSpawnInterval = this.getConfig().getInt("auto-spawn-interval");
|
||||
this.timeUntilSpawn = this.autoSpawnInterval;
|
||||
this.autoSpawnLocations = new ArrayList<>();
|
||||
for (String string : this.getConfig().getStrings("auto-spawn-locations")) {
|
||||
String[] split = string.split(":");
|
||||
@@ -448,11 +582,112 @@ public class EcoBoss extends PluginDependent<EcoPlugin> {
|
||||
autoSpawnLocations.add(new Location(world, x, y, z));
|
||||
}
|
||||
|
||||
new PlaceholderEntry(
|
||||
"timeuntilspawn_"+this.name,
|
||||
(player) -> new BigDecimal(this.timeUntilSpawn/20).setScale(1, RoundingMode.HALF_UP).toString(),
|
||||
false
|
||||
).register();
|
||||
|
||||
for (String req : config.getStrings("spawn-requirements", false)) {
|
||||
List<String> split = Arrays.asList(req.split(":"));
|
||||
if (split.size() < 2) {
|
||||
continue;
|
||||
}
|
||||
|
||||
Requirement requirement = Requirements.getByID(split.get(0).toLowerCase());
|
||||
|
||||
this.requirements.put(requirement, split.subList(1, split.size()));
|
||||
}
|
||||
|
||||
this.clearCachedRequirements();
|
||||
|
||||
// Spawn egg
|
||||
if (this.getConfig().getBool("spawn-egg.enabled")) {
|
||||
Material material = Material.getMaterial(this.getConfig().getString("spawn-egg.material").toUpperCase());
|
||||
assert material != null;
|
||||
ItemBuilder builder = new ItemStackBuilder(material)
|
||||
.setDisplayName(this.getConfig().getString("spawn-egg.name"))
|
||||
.addLoreLines(this.getConfig().getStrings("spawn-egg.lore"))
|
||||
.writeMetaKey(this.getPlugin().getNamespacedKeyFactory().create("spawn_egg"), PersistentDataType.STRING, this.getName());
|
||||
|
||||
if (this.getConfig().getBool("spawn-egg.glow")) {
|
||||
builder.addEnchantment(Enchantment.DURABILITY, 1)
|
||||
.addItemFlag(ItemFlag.HIDE_ENCHANTS);
|
||||
}
|
||||
|
||||
this.spawnEgg = builder.build();
|
||||
|
||||
if (this.getConfig().getBool("spawn-egg.craftable")) {
|
||||
Recipes.createAndRegisterRecipe(
|
||||
this.getPlugin(),
|
||||
"spawn_egg_" + this.getName(),
|
||||
this.getSpawnEgg(),
|
||||
this.getConfig().getStrings("spawn-egg.recipe", false)
|
||||
);
|
||||
}
|
||||
} else {
|
||||
this.spawnEgg = null;
|
||||
}
|
||||
|
||||
if (this.getConfig().getBool("enabled")) {
|
||||
EcoBosses.addBoss(this);
|
||||
}
|
||||
}
|
||||
|
||||
/**
|
||||
* Clear requirements cache.
|
||||
*/
|
||||
public void clearCachedRequirements() {
|
||||
this.cachedRequirements.clear();
|
||||
}
|
||||
|
||||
/**
|
||||
* Does the player meet the requirements to use this enchantment.
|
||||
*
|
||||
* @param player The player.
|
||||
* @return If the requirements are met.
|
||||
*/
|
||||
public boolean areRequirementsMet(@NotNull final Player player) {
|
||||
if (cachedRequirements.containsKey(player.getUniqueId())) {
|
||||
return cachedRequirements.get(player.getUniqueId());
|
||||
}
|
||||
|
||||
for (Map.Entry<Requirement, List<String>> entry : requirements.entrySet()) {
|
||||
if (!entry.getKey().doesPlayerMeet(player, entry.getValue())) {
|
||||
cachedRequirements.put(player.getUniqueId(), false);
|
||||
return false;
|
||||
}
|
||||
}
|
||||
|
||||
cachedRequirements.put(player.getUniqueId(), true);
|
||||
return true;
|
||||
}
|
||||
|
||||
public List<ItemStack> generateDrops() {
|
||||
List<ItemStack> drops = new ArrayList<>();
|
||||
|
||||
for (String dropName : this.drops) {
|
||||
double chance = 100;
|
||||
if (dropName.contains("::")) {
|
||||
String[] split = dropName.split("::");
|
||||
chance = Double.parseDouble(split[0]);
|
||||
dropName = split[1];
|
||||
}
|
||||
|
||||
ItemStack itemStack = Items.lookup(dropName).getItem();
|
||||
if (itemStack.getType() == Material.AIR) {
|
||||
Bukkit.getLogger().warning(this.getName() + " has an invalid drop configured! (" + dropName + ")");
|
||||
continue;
|
||||
}
|
||||
|
||||
if (NumberUtils.randFloat(0, 100) <= chance) {
|
||||
drops.add(itemStack);
|
||||
}
|
||||
}
|
||||
|
||||
return drops;
|
||||
}
|
||||
|
||||
/**
|
||||
* Create effect tickers for Living Boss.
|
||||
*
|
||||
@@ -460,9 +695,9 @@ public class EcoBoss extends PluginDependent<EcoPlugin> {
|
||||
*/
|
||||
public List<Effect> createEffects() {
|
||||
List<Effect> effects = new ArrayList<>();
|
||||
this.effectNames.forEach((string, args) -> {
|
||||
effects.add(Effects.getEffect(string, args));
|
||||
});
|
||||
for (ArgumentedEffectName effectName : this.effectNames) {
|
||||
effects.add(Effects.getEffect(effectName.name(), effectName.args()));
|
||||
}
|
||||
|
||||
return effects;
|
||||
}
|
||||
|
||||
@@ -29,7 +29,7 @@ public class EcoBosses {
|
||||
* Sets that exist by default.
|
||||
*/
|
||||
private static final List<String> DEFAULT_BOSSES = Arrays.asList(
|
||||
"illusioner",
|
||||
"dark_guardian",
|
||||
"tarantula",
|
||||
"steel_golem",
|
||||
"alpha_wolf"
|
||||
|
||||
@@ -3,23 +3,29 @@ package com.willfp.ecobosses.bosses;
|
||||
import com.willfp.eco.core.EcoPlugin;
|
||||
import com.willfp.eco.core.PluginDependent;
|
||||
import com.willfp.eco.core.scheduling.RunnableTask;
|
||||
import com.willfp.eco.util.NumberUtils;
|
||||
import com.willfp.eco.util.StringUtils;
|
||||
import com.willfp.ecobosses.bosses.effects.Effect;
|
||||
import com.willfp.ecobosses.bosses.tick.BossTicker;
|
||||
import com.willfp.ecobosses.bosses.tick.tickers.BossBarTicker;
|
||||
import com.willfp.ecobosses.bosses.tick.tickers.HealthPlaceholderTicker;
|
||||
import com.willfp.ecobosses.bosses.tick.tickers.DeathTimeTicker;
|
||||
import com.willfp.ecobosses.bosses.tick.tickers.NamePlaceholderTicker;
|
||||
import com.willfp.ecobosses.bosses.tick.tickers.TargetTicker;
|
||||
import com.willfp.ecobosses.bosses.util.obj.EquipmentPiece;
|
||||
import com.willfp.ecobosses.bosses.util.obj.OptionedSound;
|
||||
import lombok.Getter;
|
||||
import net.kyori.adventure.bossbar.BossBar;
|
||||
import org.bukkit.Bukkit;
|
||||
import org.bukkit.attribute.Attribute;
|
||||
import org.bukkit.attribute.AttributeInstance;
|
||||
import org.bukkit.attribute.AttributeModifier;
|
||||
import org.bukkit.boss.BarFlag;
|
||||
import org.bukkit.entity.Ageable;
|
||||
import org.bukkit.entity.LivingEntity;
|
||||
import org.bukkit.entity.Player;
|
||||
import org.bukkit.inventory.EntityEquipment;
|
||||
import org.bukkit.inventory.EquipmentSlot;
|
||||
import org.bukkit.persistence.PersistentDataType;
|
||||
import org.bukkit.potion.PotionEffect;
|
||||
import org.bukkit.potion.PotionEffectType;
|
||||
import org.jetbrains.annotations.NotNull;
|
||||
|
||||
import java.util.ArrayList;
|
||||
@@ -66,17 +72,17 @@ public class LivingEcoBoss extends PluginDependent<EcoPlugin> {
|
||||
|
||||
// Tickers
|
||||
this.tickers = new ArrayList<>();
|
||||
this.tickers.add(new HealthPlaceholderTicker());
|
||||
this.tickers.add(new NamePlaceholderTicker());
|
||||
this.tickers.add(new DeathTimeTicker());
|
||||
this.tickers.add(new TargetTicker(boss.getTargetMode(), boss.getTargetDistance()));
|
||||
if (boss.isBossbarEnabled()) {
|
||||
this.tickers.add(
|
||||
new BossBarTicker(
|
||||
Bukkit.getServer().createBossBar(
|
||||
plugin.getNamespacedKeyFactory().create("boss_" + NumberUtils.randInt(0, 1000000)),
|
||||
entity.getCustomName(),
|
||||
BossBar.bossBar(
|
||||
StringUtils.toComponent(entity.getCustomName()),
|
||||
1,
|
||||
boss.getBossbarProperties().color(),
|
||||
boss.getBossbarProperties().style(),
|
||||
(BarFlag) null
|
||||
boss.getBossbarProperties().style()
|
||||
),
|
||||
this.getPlugin().getConfigYml().getInt("bossbar-radius")
|
||||
)
|
||||
@@ -96,9 +102,49 @@ public class LivingEcoBoss extends PluginDependent<EcoPlugin> {
|
||||
entity.setPersistent(true);
|
||||
entity.setRemoveWhenFarAway(false);
|
||||
|
||||
if (boss.isGlowing()) entity.addPotionEffect(new PotionEffect(PotionEffectType.GLOWING, Integer.MAX_VALUE, 1, false, false, false));
|
||||
|
||||
if (entity instanceof Ageable ageable) {
|
||||
if (boss.isBaby()) ageable.setBaby();
|
||||
else ageable.setAdult();
|
||||
}
|
||||
|
||||
if (boss.getTimeToLive() > 0) {
|
||||
entity.setMetadata("death-time", this.getPlugin().getMetadataValueFactory().create(System.currentTimeMillis() + (boss.getTimeToLive() * 1000L)));
|
||||
}
|
||||
|
||||
entity.setCustomName(boss.getDisplayName());
|
||||
entity.setCustomNameVisible(true);
|
||||
|
||||
EntityEquipment equipment = entity.getEquipment();
|
||||
if (equipment != null) {
|
||||
EquipmentPiece head = boss.getEquipment().get(EquipmentSlot.HEAD);
|
||||
EquipmentPiece chest = boss.getEquipment().get(EquipmentSlot.CHEST);
|
||||
EquipmentPiece legs = boss.getEquipment().get(EquipmentSlot.LEGS);
|
||||
EquipmentPiece boots = boss.getEquipment().get(EquipmentSlot.FEET);
|
||||
EquipmentPiece hand = boss.getEquipment().get(EquipmentSlot.HAND);
|
||||
if (head != null) {
|
||||
equipment.setHelmet(head.itemStack(), true);
|
||||
equipment.setHelmetDropChance((float) head.chance());
|
||||
}
|
||||
if (chest != null) {
|
||||
equipment.setChestplate(chest.itemStack(), true);
|
||||
equipment.setChestplateDropChance((float) chest.chance());
|
||||
}
|
||||
if (legs != null) {
|
||||
equipment.setLeggings(legs.itemStack(), true);
|
||||
equipment.setLeggingsDropChance((float) legs.chance());
|
||||
}
|
||||
if (boots != null) {
|
||||
equipment.setBoots(boots.itemStack(), true);
|
||||
equipment.setBootsDropChance((float) boots.chance());
|
||||
}
|
||||
if (hand != null) {
|
||||
equipment.setItemInMainHand(hand.itemStack(), true);
|
||||
equipment.setItemInMainHandDropChance((float) hand.chance());
|
||||
}
|
||||
}
|
||||
|
||||
AttributeInstance movementSpeed = entity.getAttribute(Attribute.GENERIC_MOVEMENT_SPEED);
|
||||
assert movementSpeed != null;
|
||||
movementSpeed.addModifier(new AttributeModifier(entity.getUniqueId(), "ecobosses-movement-multiplier", boss.getMovementSpeedMultiplier() - 1, AttributeModifier.Operation.MULTIPLY_SCALAR_1));
|
||||
|
||||
@@ -9,7 +9,6 @@ import com.willfp.ecobosses.bosses.util.obj.DamagerProperty;
|
||||
import com.willfp.ecobosses.bosses.util.obj.ImmunityOptions;
|
||||
import org.bukkit.entity.LivingEntity;
|
||||
import org.bukkit.entity.Player;
|
||||
import org.bukkit.entity.Projectile;
|
||||
import org.bukkit.event.EventHandler;
|
||||
import org.bukkit.event.EventPriority;
|
||||
import org.bukkit.event.Listener;
|
||||
@@ -56,7 +55,9 @@ public class AttackListeners extends PluginDependent<EcoPlugin> implements Liste
|
||||
|
||||
LivingEcoBoss livingEcoBoss = boss.getLivingBoss(entity);
|
||||
|
||||
BossUtils.warnIfNull(livingEcoBoss);
|
||||
if (livingEcoBoss == null) {
|
||||
return;
|
||||
}
|
||||
|
||||
if (boss.isAttackOnInjure()) {
|
||||
livingEcoBoss.handleAttack(player);
|
||||
@@ -124,7 +125,9 @@ public class AttackListeners extends PluginDependent<EcoPlugin> implements Liste
|
||||
|
||||
LivingEcoBoss livingEcoBoss = boss.getLivingBoss(entity);
|
||||
|
||||
BossUtils.warnIfNull(livingEcoBoss);
|
||||
if (livingEcoBoss == null) {
|
||||
return;
|
||||
}
|
||||
|
||||
livingEcoBoss.handleAttack(player);
|
||||
}
|
||||
@@ -151,6 +154,7 @@ public class AttackListeners extends PluginDependent<EcoPlugin> implements Liste
|
||||
if (immunities.immuneToFire()
|
||||
&& (event.getCause() == EntityDamageEvent.DamageCause.FIRE
|
||||
|| event.getCause() == EntityDamageEvent.DamageCause.FIRE_TICK
|
||||
|| event.getCause() == EntityDamageEvent.DamageCause.LAVA
|
||||
|| event.getCause() == EntityDamageEvent.DamageCause.HOT_FLOOR)) {
|
||||
event.setCancelled(true);
|
||||
}
|
||||
|
||||
@@ -3,7 +3,8 @@ package com.willfp.ecobosses.bosses.listeners;
|
||||
import com.willfp.eco.util.NumberUtils;
|
||||
import com.willfp.ecobosses.bosses.EcoBoss;
|
||||
import com.willfp.ecobosses.bosses.EcoBosses;
|
||||
import com.willfp.ecobosses.bosses.util.BossUtils;
|
||||
import com.willfp.ecobosses.events.EcoBossSpawnTimerEvent;
|
||||
import org.bukkit.Bukkit;
|
||||
import org.bukkit.Location;
|
||||
import org.bukkit.World;
|
||||
import org.bukkit.entity.Entity;
|
||||
@@ -32,8 +33,9 @@ public class AutoSpawnTimer implements Runnable {
|
||||
Set<World> worlds = new HashSet<>();
|
||||
|
||||
for (Entity entity : boss.getLivingBosses().keySet()) {
|
||||
BossUtils.warnIfNull(entity);
|
||||
assert entity != null;
|
||||
if (entity == null) {
|
||||
continue;
|
||||
}
|
||||
|
||||
worlds.add(entity.getWorld());
|
||||
}
|
||||
@@ -45,9 +47,16 @@ public class AutoSpawnTimer implements Runnable {
|
||||
continue;
|
||||
}
|
||||
|
||||
boss.setTimeUntilSpawn(boss.getTimeUntilSpawn()-1);
|
||||
|
||||
if (tick % boss.getAutoSpawnInterval() == 0) {
|
||||
Location location = locations.get(NumberUtils.randInt(0, locations.size() - 1));
|
||||
EcoBossSpawnTimerEvent event = new EcoBossSpawnTimerEvent(boss, location);
|
||||
Bukkit.getServer().getPluginManager().callEvent(event);
|
||||
if (!event.isCancelled()) {
|
||||
boss.spawn(location);
|
||||
boss.setTimeUntilSpawn(boss.getAutoSpawnInterval());
|
||||
}
|
||||
}
|
||||
}
|
||||
}
|
||||
|
||||
@@ -19,6 +19,7 @@ import org.bukkit.event.EventHandler;
|
||||
import org.bukkit.event.EventPriority;
|
||||
import org.bukkit.event.Listener;
|
||||
import org.bukkit.event.entity.EntityDeathEvent;
|
||||
import org.bukkit.event.entity.SlimeSplitEvent;
|
||||
import org.bukkit.inventory.ItemStack;
|
||||
import org.jetbrains.annotations.NotNull;
|
||||
|
||||
@@ -130,12 +131,7 @@ public class DeathListeners extends PluginDependent<EcoPlugin> implements Listen
|
||||
}
|
||||
}
|
||||
|
||||
List<ItemStack> drops = new ArrayList<>();
|
||||
for (Map.Entry<ItemStack, Double> entry : boss.getDrops().entrySet()) {
|
||||
if (NumberUtils.randFloat(0, 100) < entry.getValue()) {
|
||||
drops.add(entry.getKey().clone());
|
||||
}
|
||||
}
|
||||
List<ItemStack> drops = boss.generateDrops();
|
||||
|
||||
for (Entity nearby : entity.getNearbyEntities(boss.getNearbyRadius(), boss.getNearbyRadius(), boss.getNearbyRadius())) {
|
||||
if (nearby instanceof Player) {
|
||||
@@ -151,4 +147,17 @@ public class DeathListeners extends PluginDependent<EcoPlugin> implements Listen
|
||||
event.getDrops().addAll(drops);
|
||||
event.setDroppedExp(boss.getExperienceOptions().generateXp());
|
||||
}
|
||||
|
||||
@EventHandler
|
||||
public void preventSplit(@NotNull final SlimeSplitEvent event) {
|
||||
LivingEntity entity = event.getEntity();
|
||||
|
||||
EcoBoss boss = BossUtils.getBoss(entity);
|
||||
|
||||
if (boss == null) {
|
||||
return;
|
||||
}
|
||||
|
||||
event.setCancelled(true);
|
||||
}
|
||||
}
|
||||
|
||||
@@ -9,6 +9,7 @@ import org.bukkit.entity.LivingEntity;
|
||||
import org.bukkit.entity.Minecart;
|
||||
import org.bukkit.event.EventHandler;
|
||||
import org.bukkit.event.Listener;
|
||||
import org.bukkit.event.entity.EntityPickupItemEvent;
|
||||
import org.jetbrains.annotations.NotNull;
|
||||
import org.spigotmc.event.entity.EntityMountEvent;
|
||||
|
||||
@@ -28,7 +29,7 @@ public class PassiveListeners extends PluginDependent<EcoPlugin> implements List
|
||||
* @param event The event to listen for.
|
||||
*/
|
||||
@EventHandler(ignoreCancelled = true)
|
||||
public void onAttackBoss(@NotNull final EntityMountEvent event) {
|
||||
public void onMount(@NotNull final EntityMountEvent event) {
|
||||
if (!(event.getEntity() instanceof LivingEntity entity)) {
|
||||
return;
|
||||
}
|
||||
@@ -47,4 +48,15 @@ public class PassiveListeners extends PluginDependent<EcoPlugin> implements List
|
||||
event.setCancelled(true);
|
||||
}
|
||||
}
|
||||
|
||||
@EventHandler
|
||||
public void onPickup(@NotNull final EntityPickupItemEvent event) {
|
||||
EcoBoss boss = BossUtils.getBoss(event.getEntity());
|
||||
|
||||
if (boss == null) {
|
||||
return;
|
||||
}
|
||||
|
||||
event.setCancelled(true);
|
||||
}
|
||||
}
|
||||
|
||||
@@ -5,11 +5,21 @@ import com.willfp.eco.core.PluginDependent;
|
||||
import com.willfp.ecobosses.bosses.EcoBoss;
|
||||
import com.willfp.ecobosses.bosses.EcoBosses;
|
||||
import com.willfp.ecobosses.bosses.util.obj.SpawnTotem;
|
||||
import com.willfp.ecobosses.events.EcoBossSpawnEggEvent;
|
||||
import com.willfp.ecobosses.events.EcoBossSpawnTotemEvent;
|
||||
import org.bukkit.Material;
|
||||
import org.bukkit.block.Block;
|
||||
import org.bukkit.event.Event;
|
||||
import org.bukkit.event.EventHandler;
|
||||
import org.bukkit.event.Listener;
|
||||
import org.bukkit.event.block.Action;
|
||||
import org.bukkit.event.block.BlockPlaceEvent;
|
||||
import org.bukkit.event.player.PlayerInteractEvent;
|
||||
import org.bukkit.inventory.EquipmentSlot;
|
||||
import org.bukkit.inventory.ItemStack;
|
||||
import org.bukkit.inventory.meta.ItemMeta;
|
||||
import org.bukkit.persistence.PersistentDataContainer;
|
||||
import org.bukkit.persistence.PersistentDataType;
|
||||
import org.jetbrains.annotations.NotNull;
|
||||
|
||||
public class SpawnListeners extends PluginDependent<EcoPlugin> implements Listener {
|
||||
@@ -54,10 +64,20 @@ public class SpawnListeners extends PluginDependent<EcoPlugin> implements Listen
|
||||
if (boss.isSpawnTotemEnabled()) {
|
||||
if (!boss.getSpawnTotemDisabledWorldNames().contains(event.getBlock().getWorld().getName().toLowerCase())) {
|
||||
if (boss.getSpawnTotem().equals(placedTotem)) {
|
||||
|
||||
if (!boss.areRequirementsMet(event.getPlayer())) {
|
||||
event.getPlayer().sendMessage(this.getPlugin().getLangYml().getMessage("requirements-not-met"));
|
||||
return;
|
||||
}
|
||||
|
||||
EcoBossSpawnTotemEvent eggEvent = new EcoBossSpawnTotemEvent(boss, event.getPlayer(), event.getBlock().getLocation(), placedTotem);
|
||||
|
||||
this.getPlugin().getServer().getPluginManager().callEvent(eggEvent);
|
||||
|
||||
if (!eggEvent.isCancelled()) {
|
||||
block1.setType(Material.AIR);
|
||||
block2.setType(Material.AIR);
|
||||
block3.setType(Material.AIR);
|
||||
|
||||
boss.spawn(event.getBlock().getLocation());
|
||||
}
|
||||
}
|
||||
@@ -66,3 +86,69 @@ public class SpawnListeners extends PluginDependent<EcoPlugin> implements Listen
|
||||
}
|
||||
}
|
||||
}
|
||||
|
||||
@EventHandler
|
||||
public void spawnEgg(@NotNull final PlayerInteractEvent event) {
|
||||
if (event.getAction() != Action.RIGHT_CLICK_BLOCK) {
|
||||
return;
|
||||
}
|
||||
|
||||
ItemStack item = event.getItem();
|
||||
if (item == null) {
|
||||
return;
|
||||
}
|
||||
|
||||
ItemMeta meta = item.getItemMeta();
|
||||
if (meta == null) {
|
||||
return;
|
||||
}
|
||||
|
||||
PersistentDataContainer container = meta.getPersistentDataContainer();
|
||||
if (!container.has(this.getPlugin().getNamespacedKeyFactory().create("spawn_egg"), PersistentDataType.STRING)) {
|
||||
return;
|
||||
}
|
||||
|
||||
String id = container.get(this.getPlugin().getNamespacedKeyFactory().create("spawn_egg"), PersistentDataType.STRING);
|
||||
if (id == null) {
|
||||
return;
|
||||
}
|
||||
|
||||
EcoBoss boss = EcoBosses.getByName(id);
|
||||
if (boss == null) {
|
||||
return;
|
||||
}
|
||||
|
||||
event.setCancelled(true);
|
||||
event.setUseItemInHand(Event.Result.DENY);
|
||||
|
||||
if (!boss.areRequirementsMet(event.getPlayer())) {
|
||||
event.getPlayer().sendMessage(this.getPlugin().getLangYml().getMessage("requirements-not-met"));
|
||||
return;
|
||||
}
|
||||
|
||||
EcoBossSpawnEggEvent eggEvent = new EcoBossSpawnEggEvent(boss, event.getPlayer(), event.getClickedBlock().getLocation(), item);
|
||||
|
||||
this.getPlugin().getServer().getPluginManager().callEvent(eggEvent);
|
||||
|
||||
if (eggEvent.isCancelled()) {
|
||||
return;
|
||||
}
|
||||
|
||||
item.setAmount(item.getAmount() - 1);
|
||||
|
||||
if (event.getHand() == EquipmentSlot.HAND) {
|
||||
ItemStack hand = event.getPlayer().getInventory().getItemInMainHand();
|
||||
hand.setAmount(hand.getAmount() - 1);
|
||||
} else {
|
||||
ItemStack hand = event.getPlayer().getInventory().getItemInOffHand();
|
||||
hand.setAmount(hand.getAmount() - 1);
|
||||
}
|
||||
|
||||
Block block = event.getClickedBlock();
|
||||
if (block == null) {
|
||||
return;
|
||||
}
|
||||
|
||||
boss.spawn(block.getLocation().add(0, 1.5, 0));
|
||||
}
|
||||
}
|
||||
|
||||
@@ -1,11 +1,12 @@
|
||||
package com.willfp.ecobosses.bosses.tick.tickers;
|
||||
|
||||
import com.willfp.eco.util.PlayerUtils;
|
||||
import com.willfp.eco.util.StringUtils;
|
||||
import com.willfp.ecobosses.bosses.EcoBoss;
|
||||
import com.willfp.ecobosses.bosses.tick.BossTicker;
|
||||
import net.kyori.adventure.bossbar.BossBar;
|
||||
import org.bukkit.Bukkit;
|
||||
import org.bukkit.attribute.Attribute;
|
||||
import org.bukkit.boss.BossBar;
|
||||
import org.bukkit.boss.KeyedBossBar;
|
||||
import org.bukkit.entity.LivingEntity;
|
||||
import org.bukkit.entity.Player;
|
||||
import org.jetbrains.annotations.NotNull;
|
||||
@@ -37,14 +38,16 @@ public class BossBarTicker implements BossTicker {
|
||||
public void tick(@NotNull final EcoBoss boss,
|
||||
@NotNull final LivingEntity entity,
|
||||
final long tick) {
|
||||
bossBar.setTitle(entity.getCustomName());
|
||||
bossBar.setProgress(entity.getHealth() / entity.getAttribute(Attribute.GENERIC_MAX_HEALTH).getValue());
|
||||
bossBar.name(StringUtils.toComponent(entity.getCustomName()));
|
||||
bossBar.progress((float) (entity.getHealth() / entity.getAttribute(Attribute.GENERIC_MAX_HEALTH).getValue()));
|
||||
|
||||
if (tick % 40 == 0) {
|
||||
bossBar.removeAll();
|
||||
for (Player player : Bukkit.getOnlinePlayers()) {
|
||||
PlayerUtils.getAudience(player).hideBossBar(bossBar);
|
||||
}
|
||||
entity.getNearbyEntities(radius, radius, radius).forEach(entity1 -> {
|
||||
if (entity1 instanceof Player) {
|
||||
bossBar.addPlayer((Player) entity1);
|
||||
PlayerUtils.getAudience((Player) entity1).showBossBar(bossBar);
|
||||
}
|
||||
});
|
||||
}
|
||||
@@ -54,8 +57,8 @@ public class BossBarTicker implements BossTicker {
|
||||
public void onDeath(@NotNull final EcoBoss boss,
|
||||
@Nullable final LivingEntity entity,
|
||||
final long tick) {
|
||||
bossBar.removeAll();
|
||||
bossBar.setVisible(false);
|
||||
Bukkit.removeBossBar(((KeyedBossBar) bossBar).getKey());
|
||||
for (Player player : Bukkit.getOnlinePlayers()) {
|
||||
PlayerUtils.getAudience(player).hideBossBar(bossBar);
|
||||
}
|
||||
}
|
||||
}
|
||||
|
||||
@@ -0,0 +1,35 @@
|
||||
package com.willfp.ecobosses.bosses.tick.tickers;
|
||||
|
||||
import com.willfp.ecobosses.bosses.EcoBoss;
|
||||
import com.willfp.ecobosses.bosses.tick.BossTicker;
|
||||
import com.willfp.ecobosses.bosses.util.obj.OptionedSound;
|
||||
import org.bukkit.Bukkit;
|
||||
import org.bukkit.entity.LivingEntity;
|
||||
import org.jetbrains.annotations.NotNull;
|
||||
|
||||
public class DeathTimeTicker implements BossTicker {
|
||||
@Override
|
||||
public void tick(@NotNull final EcoBoss boss,
|
||||
@NotNull final LivingEntity entity,
|
||||
final long tick) {
|
||||
if (boss.getTimeToLive() < 0) {
|
||||
return;
|
||||
}
|
||||
|
||||
int timeLeft;
|
||||
timeLeft = (int) (entity.getMetadata("death-time").get(0).asLong() - System.currentTimeMillis());
|
||||
timeLeft = (int) Math.ceil(timeLeft / 1000D);
|
||||
if (timeLeft <= 0) {
|
||||
entity.remove();
|
||||
boss.removeLivingBoss(entity);
|
||||
|
||||
for (String despawnMessage : boss.getDespawnMessages()) {
|
||||
Bukkit.broadcastMessage(despawnMessage);
|
||||
}
|
||||
|
||||
for (OptionedSound sound : boss.getDespawnSounds()) {
|
||||
entity.getWorld().playSound(entity.getLocation(), sound.sound(), sound.volume(), sound.pitch());
|
||||
}
|
||||
}
|
||||
}
|
||||
}
|
||||
@@ -1,16 +0,0 @@
|
||||
package com.willfp.ecobosses.bosses.tick.tickers;
|
||||
|
||||
import com.willfp.eco.util.StringUtils;
|
||||
import com.willfp.ecobosses.bosses.EcoBoss;
|
||||
import com.willfp.ecobosses.bosses.tick.BossTicker;
|
||||
import org.bukkit.entity.LivingEntity;
|
||||
import org.jetbrains.annotations.NotNull;
|
||||
|
||||
public class HealthPlaceholderTicker implements BossTicker {
|
||||
@Override
|
||||
public void tick(@NotNull final EcoBoss boss,
|
||||
@NotNull final LivingEntity entity,
|
||||
final long tick) {
|
||||
entity.setCustomName(boss.getDisplayName().replace("%health%", StringUtils.internalToString(entity.getHealth())));
|
||||
}
|
||||
}
|
||||
@@ -0,0 +1,30 @@
|
||||
package com.willfp.ecobosses.bosses.tick.tickers;
|
||||
|
||||
import com.willfp.eco.util.StringUtils;
|
||||
import com.willfp.ecobosses.bosses.EcoBoss;
|
||||
import com.willfp.ecobosses.bosses.tick.BossTicker;
|
||||
import org.bukkit.entity.LivingEntity;
|
||||
import org.jetbrains.annotations.NotNull;
|
||||
|
||||
public class NamePlaceholderTicker implements BossTicker {
|
||||
@Override
|
||||
public void tick(@NotNull final EcoBoss boss,
|
||||
@NotNull final LivingEntity entity,
|
||||
final long tick) {
|
||||
int timeLeft = -1;
|
||||
if (boss.getTimeToLive() > 0) {
|
||||
timeLeft = (int) (entity.getMetadata("death-time").get(0).asLong() - System.currentTimeMillis());
|
||||
timeLeft = (int) Math.ceil(timeLeft / 1000D);
|
||||
}
|
||||
|
||||
String time = "";
|
||||
if (timeLeft > 0) {
|
||||
time = String.format("%d:%02d", timeLeft/60, timeLeft%60);
|
||||
}
|
||||
entity.setCustomName(
|
||||
boss.getDisplayName()
|
||||
.replace("%health%", StringUtils.internalToString(entity.getHealth()))
|
||||
.replace("%time%", time)
|
||||
);
|
||||
}
|
||||
}
|
||||
@@ -3,7 +3,6 @@ package com.willfp.ecobosses.bosses.util;
|
||||
import com.willfp.ecobosses.EcoBossesPlugin;
|
||||
import com.willfp.ecobosses.bosses.EcoBoss;
|
||||
import com.willfp.ecobosses.bosses.EcoBosses;
|
||||
import com.willfp.ecobosses.bosses.LivingEcoBoss;
|
||||
import com.willfp.ecobosses.bosses.util.obj.DamagerProperty;
|
||||
import lombok.experimental.UtilityClass;
|
||||
import org.bukkit.Bukkit;
|
||||
@@ -153,32 +152,4 @@ public class BossUtils {
|
||||
|
||||
return player;
|
||||
}
|
||||
|
||||
/**
|
||||
* Warn if a boss is null.
|
||||
*
|
||||
* @param boss The boss.
|
||||
*/
|
||||
public void warnIfNull(@Nullable final LivingEcoBoss boss) {
|
||||
if (boss != null) {
|
||||
return;
|
||||
}
|
||||
|
||||
PLUGIN.getLogger().severe("Boss is null! Report this to Auxilor (https://discord.gg/ZcwpSsE)");
|
||||
PLUGIN.getLogger().severe("Send this stack-trace in the relevant channel.");
|
||||
throw new NullPointerException("Boss is null!");
|
||||
}
|
||||
|
||||
/**
|
||||
* Warn if an entity is null.
|
||||
*/
|
||||
public void warnIfNull(@Nullable final Entity entity) {
|
||||
if (entity != null) {
|
||||
return;
|
||||
}
|
||||
|
||||
PLUGIN.getLogger().severe("Entity is null! Report this to Auxilor (https://discord.gg/ZcwpSsE)");
|
||||
PLUGIN.getLogger().severe("Send this stack-trace in the relevant channel.");
|
||||
throw new NullPointerException("Entity is null!");
|
||||
}
|
||||
}
|
||||
|
||||
@@ -1,12 +1,18 @@
|
||||
package com.willfp.ecobosses.bosses.util.bosstype;
|
||||
|
||||
import com.willfp.ecobosses.proxy.util.CustomEntities;
|
||||
import com.willfp.ecobosses.proxy.util.CustomEntity;
|
||||
import io.lumine.xikage.mythicmobs.MythicMobs;
|
||||
import io.lumine.xikage.mythicmobs.mobs.MythicMob;
|
||||
import lombok.Getter;
|
||||
import lombok.Setter;
|
||||
import lombok.experimental.UtilityClass;
|
||||
import org.bukkit.entity.Creeper;
|
||||
import org.bukkit.entity.EntityType;
|
||||
import org.bukkit.entity.LivingEntity;
|
||||
import org.bukkit.entity.Zombie;
|
||||
import org.jetbrains.annotations.NotNull;
|
||||
|
||||
import java.util.Arrays;
|
||||
|
||||
@UtilityClass
|
||||
@SuppressWarnings("unchecked")
|
||||
public class BossEntityUtils {
|
||||
@@ -16,18 +22,36 @@ public class BossEntityUtils {
|
||||
* @param id The name.
|
||||
* @return The boss type.
|
||||
*/
|
||||
public static BossType getBossType(@NotNull final String id) {
|
||||
public static BossType getBossType(@NotNull String id) {
|
||||
|
||||
if (id.startsWith("mythicmobs:")) {
|
||||
int level;
|
||||
|
||||
try {
|
||||
level = Integer.parseInt(Arrays.stream(id.split("_")).toList().get(id.split("_").length - 1));
|
||||
} catch (NumberFormatException exception) {
|
||||
level = 1;
|
||||
}
|
||||
|
||||
MythicMob mob = MythicMobs.inst().getMobManager().getMythicMob(id.replace("mythicmobs:", "")
|
||||
.replace("_" + level, ""));
|
||||
|
||||
if (mob != null) {
|
||||
return new MythicMobsBossType(mob, level);
|
||||
}
|
||||
}
|
||||
|
||||
if (id.equalsIgnoreCase("charged_creeper")) {
|
||||
return new ChargedCreeperBossType();
|
||||
}
|
||||
|
||||
try {
|
||||
Class<? extends LivingEntity> type = (Class<? extends LivingEntity>) EntityType.valueOf(id.toUpperCase()).getEntityClass();
|
||||
assert type != null;
|
||||
return new VanillaBossType(type);
|
||||
} catch (IllegalArgumentException e) {
|
||||
Class<? extends CustomEntity<? extends LivingEntity>> proxy = CustomEntities.getEntityClass(id.toLowerCase());
|
||||
if (proxy != null) {
|
||||
return new CustomBossType(proxy);
|
||||
}
|
||||
} catch (IllegalArgumentException ignored) {
|
||||
}
|
||||
|
||||
return null;
|
||||
return new VanillaBossType(Zombie.class);
|
||||
}
|
||||
}
|
||||
|
||||
@@ -0,0 +1,30 @@
|
||||
package com.willfp.ecobosses.bosses.util.bosstype;
|
||||
|
||||
import org.bukkit.Location;
|
||||
import org.bukkit.entity.Creeper;
|
||||
import org.bukkit.entity.LivingEntity;
|
||||
import org.jetbrains.annotations.NotNull;
|
||||
|
||||
import java.util.Objects;
|
||||
|
||||
class ChargedCreeperBossType extends VanillaBossType {
|
||||
/**
|
||||
* Create new Charged Creeper boss type.
|
||||
*/
|
||||
ChargedCreeperBossType() {
|
||||
super(Creeper.class);
|
||||
}
|
||||
|
||||
/**
|
||||
* Spawn a charged creeper.
|
||||
*
|
||||
* @param location The location.
|
||||
* @return The entity.
|
||||
*/
|
||||
@Override
|
||||
public LivingEntity spawnBossEntity(@NotNull final Location location) {
|
||||
Creeper creeper = Objects.requireNonNull(location.getWorld()).spawn(location, Creeper.class);
|
||||
creeper.setPowered(true);
|
||||
return creeper;
|
||||
}
|
||||
}
|
||||
@@ -1,29 +0,0 @@
|
||||
package com.willfp.ecobosses.bosses.util.bosstype;
|
||||
|
||||
import com.willfp.ecobosses.EcoBossesPlugin;
|
||||
import com.willfp.ecobosses.proxy.proxies.CustomEntitySpawnerProxy;
|
||||
import com.willfp.ecobosses.proxy.util.CustomEntity;
|
||||
import org.bukkit.Location;
|
||||
import org.bukkit.entity.LivingEntity;
|
||||
import org.jetbrains.annotations.NotNull;
|
||||
|
||||
class CustomBossType extends BossType {
|
||||
/**
|
||||
* The entity type.
|
||||
*/
|
||||
private final Class<? extends CustomEntity<? extends LivingEntity>> entityClass;
|
||||
|
||||
/**
|
||||
* Create new vanilla boss type.
|
||||
*
|
||||
* @param entityClass The entity class.
|
||||
*/
|
||||
CustomBossType(@NotNull final Class<? extends CustomEntity<? extends LivingEntity>> entityClass) {
|
||||
this.entityClass = entityClass;
|
||||
}
|
||||
|
||||
@Override
|
||||
public LivingEntity spawnBossEntity(@NotNull final Location location) {
|
||||
return EcoBossesPlugin.getInstance().getProxy(CustomEntitySpawnerProxy.class).spawnCustomEntity(entityClass, location);
|
||||
}
|
||||
}
|
||||
@@ -0,0 +1,46 @@
|
||||
package com.willfp.ecobosses.bosses.util.bosstype;
|
||||
|
||||
import io.lumine.xikage.mythicmobs.MythicMobs;
|
||||
import io.lumine.xikage.mythicmobs.adapters.AbstractLocation;
|
||||
import io.lumine.xikage.mythicmobs.adapters.AbstractWorld;
|
||||
import io.lumine.xikage.mythicmobs.api.exceptions.InvalidMobTypeException;
|
||||
import io.lumine.xikage.mythicmobs.mobs.MythicMob;
|
||||
import org.bukkit.Location;
|
||||
import org.bukkit.entity.LivingEntity;
|
||||
import org.jetbrains.annotations.NotNull;
|
||||
|
||||
public class MythicMobsBossType extends BossType {
|
||||
|
||||
/**
|
||||
* The entity type.
|
||||
*/
|
||||
private final MythicMob boss;
|
||||
|
||||
/**
|
||||
* Level of MythicMobs mob
|
||||
*/
|
||||
private final int level;
|
||||
|
||||
/**
|
||||
* Create new vanilla boss type.
|
||||
*
|
||||
* @param boss The MythicMob.
|
||||
*/
|
||||
public MythicMobsBossType(MythicMob boss, int level) {
|
||||
this.boss = boss;
|
||||
this.level = level;
|
||||
}
|
||||
|
||||
|
||||
@Override
|
||||
public LivingEntity spawnBossEntity(@NotNull Location location) {
|
||||
try {
|
||||
return (LivingEntity) MythicMobs.inst().getAPIHelper().spawnMythicMob(boss, location, level);
|
||||
} catch (InvalidMobTypeException e) {
|
||||
e.printStackTrace();
|
||||
}
|
||||
return null;
|
||||
}
|
||||
|
||||
|
||||
}
|
||||
@@ -1,6 +1,7 @@
|
||||
package com.willfp.ecobosses.bosses.util.bosstype;
|
||||
|
||||
import org.bukkit.Location;
|
||||
import org.bukkit.entity.Creeper;
|
||||
import org.bukkit.entity.LivingEntity;
|
||||
import org.jetbrains.annotations.NotNull;
|
||||
|
||||
@@ -23,6 +24,7 @@ class VanillaBossType extends BossType {
|
||||
|
||||
@Override
|
||||
public LivingEntity spawnBossEntity(@NotNull final Location location) {
|
||||
return Objects.requireNonNull(location.getWorld()).spawn(location, entityClass);
|
||||
LivingEntity result = Objects.requireNonNull(location.getWorld()).spawn(location, entityClass);
|
||||
return result;
|
||||
}
|
||||
}
|
||||
|
||||
@@ -0,0 +1,8 @@
|
||||
package com.willfp.ecobosses.bosses.util.obj;
|
||||
|
||||
import org.jetbrains.annotations.NotNull;
|
||||
|
||||
import java.util.List;
|
||||
|
||||
public record ArgumentedEffectName(@NotNull String name, @NotNull List<String> args) {
|
||||
}
|
||||
@@ -1,9 +1,7 @@
|
||||
package com.willfp.ecobosses.bosses.util.obj;
|
||||
|
||||
import lombok.Data;
|
||||
import org.bukkit.boss.BarColor;
|
||||
import org.bukkit.boss.BarStyle;
|
||||
import net.kyori.adventure.bossbar.BossBar;
|
||||
|
||||
public record BossbarProperties(BarColor color, BarStyle style) {
|
||||
public record BossbarProperties(BossBar.Color color, BossBar.Overlay style) {
|
||||
|
||||
}
|
||||
|
||||
@@ -0,0 +1,8 @@
|
||||
package com.willfp.ecobosses.bosses.util.obj;
|
||||
|
||||
import org.bukkit.inventory.ItemStack;
|
||||
import org.jetbrains.annotations.NotNull;
|
||||
|
||||
public record EquipmentPiece(@NotNull ItemStack itemStack,
|
||||
double chance) {
|
||||
}
|
||||
@@ -1,41 +0,0 @@
|
||||
package com.willfp.ecobosses.commands;
|
||||
|
||||
import com.willfp.eco.core.command.CommandHandler;
|
||||
import com.willfp.eco.core.command.impl.Subcommand;
|
||||
import com.willfp.ecobosses.EcoBossesPlugin;
|
||||
import org.bukkit.Bukkit;
|
||||
import org.bukkit.configuration.file.YamlConfiguration;
|
||||
import org.bukkit.entity.Player;
|
||||
import org.bukkit.inventory.ItemStack;
|
||||
import org.jetbrains.annotations.NotNull;
|
||||
|
||||
import java.util.Base64;
|
||||
|
||||
public class CommandBase64 extends Subcommand {
|
||||
/**
|
||||
* Instantiate a new executor for /ebdrop.
|
||||
*
|
||||
* @param plugin The plugin to manage the execution for.
|
||||
*/
|
||||
public CommandBase64(@NotNull final EcoBossesPlugin plugin) {
|
||||
super(plugin, "base64", "ecobosses.command.base64", true);
|
||||
}
|
||||
|
||||
@Override
|
||||
public CommandHandler getHandler() {
|
||||
return (sender, args) -> {
|
||||
Player player = (Player) sender;
|
||||
ItemStack itemStack = player.getInventory().getItemInMainHand();
|
||||
String key = "drop-key";
|
||||
YamlConfiguration jank = new YamlConfiguration();
|
||||
jank.set(key, itemStack);
|
||||
String configString = jank.saveToString();
|
||||
String dropString = Base64.getEncoder().encodeToString(configString.getBytes());
|
||||
|
||||
Bukkit.getLogger().info("Copy this into the drops section of your boss yml!");
|
||||
Bukkit.getLogger().info("\n" + dropString);
|
||||
|
||||
player.sendMessage(this.getPlugin().getLangYml().getMessage("sent-drop"));
|
||||
};
|
||||
}
|
||||
}
|
||||
@@ -16,7 +16,7 @@ public class CommandEcobosses extends PluginCommand {
|
||||
this.addSubcommand(new CommandReload(plugin))
|
||||
.addSubcommand(new CommandKillall(plugin))
|
||||
.addSubcommand(new CommandSpawn(plugin))
|
||||
.addSubcommand(new CommandBase64(plugin));
|
||||
.addSubcommand(new CommandGive(plugin));
|
||||
}
|
||||
|
||||
@Override
|
||||
|
||||
@@ -0,0 +1,151 @@
|
||||
package com.willfp.ecobosses.commands;
|
||||
|
||||
|
||||
import com.willfp.eco.core.EcoPlugin;
|
||||
import com.willfp.eco.core.command.CommandHandler;
|
||||
import com.willfp.eco.core.command.TabCompleteHandler;
|
||||
import com.willfp.eco.core.command.impl.Subcommand;
|
||||
import com.willfp.eco.core.config.updating.ConfigUpdater;
|
||||
import com.willfp.ecobosses.bosses.EcoBoss;
|
||||
import com.willfp.ecobosses.bosses.EcoBosses;
|
||||
import org.bukkit.Bukkit;
|
||||
import org.bukkit.entity.Player;
|
||||
import org.bukkit.inventory.ItemStack;
|
||||
import org.bukkit.util.StringUtil;
|
||||
import org.jetbrains.annotations.NotNull;
|
||||
|
||||
import java.util.ArrayList;
|
||||
import java.util.Arrays;
|
||||
import java.util.Collections;
|
||||
import java.util.List;
|
||||
import java.util.stream.Collectors;
|
||||
|
||||
public class CommandGive extends Subcommand {
|
||||
/**
|
||||
* The cached names.
|
||||
*/
|
||||
private static final List<String> BOSS_NAMES = new ArrayList<>();
|
||||
|
||||
/**
|
||||
* The cached numbers.
|
||||
*/
|
||||
private static final List<String> NUMBERS = Arrays.asList(
|
||||
"1",
|
||||
"2",
|
||||
"3",
|
||||
"4",
|
||||
"5",
|
||||
"10",
|
||||
"32",
|
||||
"64"
|
||||
);
|
||||
|
||||
/**
|
||||
* Instantiate a new command handler.
|
||||
*
|
||||
* @param plugin The plugin for the commands to listen for.
|
||||
*/
|
||||
public CommandGive(@NotNull final EcoPlugin plugin) {
|
||||
super(plugin, "give", "ecobosses.command.give", false);
|
||||
}
|
||||
|
||||
/**
|
||||
* Called on reload.
|
||||
*/
|
||||
@ConfigUpdater
|
||||
public static void reload() {
|
||||
BOSS_NAMES.clear();
|
||||
BOSS_NAMES.addAll(EcoBosses.values().stream()
|
||||
.filter(boss -> boss.getSpawnEgg() != null)
|
||||
.map(EcoBoss::getName)
|
||||
.collect(Collectors.toList()));
|
||||
}
|
||||
|
||||
@Override
|
||||
public CommandHandler getHandler() {
|
||||
return (sender, args) -> {
|
||||
if (args.isEmpty()) {
|
||||
sender.sendMessage(this.getPlugin().getLangYml().getMessage("needs-player"));
|
||||
return;
|
||||
}
|
||||
|
||||
if (args.size() == 1) {
|
||||
sender.sendMessage(this.getPlugin().getLangYml().getMessage("needs-boss"));
|
||||
return;
|
||||
}
|
||||
|
||||
int amount = 1;
|
||||
|
||||
if (args.size() > 2) {
|
||||
try {
|
||||
amount = Integer.parseInt(args.get(2));
|
||||
} catch (NumberFormatException ignored) {
|
||||
// do nothing
|
||||
}
|
||||
}
|
||||
|
||||
String recieverName = args.get(0);
|
||||
Player reciever = Bukkit.getPlayer(recieverName);
|
||||
|
||||
if (reciever == null) {
|
||||
sender.sendMessage(this.getPlugin().getLangYml().getMessage("invalid-player"));
|
||||
return;
|
||||
}
|
||||
|
||||
String key = args.get(1);
|
||||
|
||||
EcoBoss boss = EcoBosses.getByName(key);
|
||||
|
||||
if (boss == null || boss.getSpawnEgg() == null) {
|
||||
sender.sendMessage(this.getPlugin().getLangYml().getMessage("invalid-boss"));
|
||||
return;
|
||||
}
|
||||
|
||||
String message = this.getPlugin().getLangYml().getMessage("give-success");
|
||||
message = message.replace("%boss%", boss.getName()).replace("%recipient%", reciever.getName());
|
||||
sender.sendMessage(message);
|
||||
|
||||
ItemStack itemStack = boss.getSpawnEgg();
|
||||
itemStack.setAmount(amount);
|
||||
reciever.getInventory().addItem(itemStack);
|
||||
};
|
||||
}
|
||||
|
||||
@Override
|
||||
public TabCompleteHandler getTabCompleter() {
|
||||
return (sender, args) -> {
|
||||
List<String> completions = new ArrayList<>();
|
||||
|
||||
if (args.isEmpty()) {
|
||||
// Currently, this case is not ever reached
|
||||
return BOSS_NAMES;
|
||||
}
|
||||
|
||||
if (args.size() == 1) {
|
||||
StringUtil.copyPartialMatches(args.get(0), Bukkit.getOnlinePlayers().stream().map(Player::getName).collect(Collectors.toList()), completions);
|
||||
return completions;
|
||||
}
|
||||
|
||||
if (args.size() == 2) {
|
||||
StringUtil.copyPartialMatches(args.get(1), BOSS_NAMES, completions);
|
||||
|
||||
Collections.sort(completions);
|
||||
return completions;
|
||||
}
|
||||
|
||||
if (args.size() == 3) {
|
||||
StringUtil.copyPartialMatches(args.get(2), NUMBERS, completions);
|
||||
|
||||
completions.sort((s1, s2) -> {
|
||||
int t1 = Integer.parseInt(s1);
|
||||
int t2 = Integer.parseInt(s2);
|
||||
return t1 - t2;
|
||||
});
|
||||
|
||||
return completions;
|
||||
}
|
||||
|
||||
return new ArrayList<>(0);
|
||||
};
|
||||
}
|
||||
}
|
||||
@@ -0,0 +1,59 @@
|
||||
package com.willfp.ecobosses.events;
|
||||
|
||||
import com.willfp.ecobosses.bosses.EcoBoss;
|
||||
import org.bukkit.Location;
|
||||
import org.bukkit.entity.Player;
|
||||
import org.bukkit.event.HandlerList;
|
||||
import org.bukkit.inventory.ItemStack;
|
||||
import org.jetbrains.annotations.NotNull;
|
||||
import org.jetbrains.annotations.Nullable;
|
||||
|
||||
public class EcoBossSpawnEggEvent extends EcoBossSpawnEvent {
|
||||
/**
|
||||
* The egg item.
|
||||
*/
|
||||
@NotNull
|
||||
private final ItemStack egg;
|
||||
|
||||
/**
|
||||
* Bukkit parity.
|
||||
*/
|
||||
private static final HandlerList HANDLERS = new HandlerList();
|
||||
|
||||
/**
|
||||
* Default constructor
|
||||
*
|
||||
* @param boss - The boss to be spawned.
|
||||
* @param player - The player that spawned this boss (can be null)
|
||||
* @param location - The location that boss will spawn at.
|
||||
* @param egg - ItemStack that represents the egg.
|
||||
*/
|
||||
public EcoBossSpawnEggEvent(@NotNull EcoBoss boss, @Nullable Player player, @NotNull Location location, @NotNull ItemStack egg) {
|
||||
super(boss, player, location);
|
||||
this.egg = egg;
|
||||
}
|
||||
|
||||
@NotNull
|
||||
public final ItemStack getEgg() {
|
||||
return this.egg;
|
||||
}
|
||||
|
||||
/**
|
||||
* Bukkit parity.
|
||||
*
|
||||
* @return The handlers.
|
||||
*/
|
||||
@Override
|
||||
public @NotNull HandlerList getHandlers() {
|
||||
return HANDLERS;
|
||||
}
|
||||
|
||||
/**
|
||||
* Bukkit parity.
|
||||
*
|
||||
* @return The handler list.
|
||||
*/
|
||||
public static HandlerList getHandlerList() {
|
||||
return HANDLERS;
|
||||
}
|
||||
}
|
||||
@@ -0,0 +1,141 @@
|
||||
package com.willfp.ecobosses.events;
|
||||
|
||||
import com.willfp.ecobosses.bosses.EcoBoss;
|
||||
import org.bukkit.Location;
|
||||
import org.bukkit.entity.Player;
|
||||
import org.bukkit.event.Cancellable;
|
||||
import org.bukkit.event.Event;
|
||||
import org.bukkit.event.HandlerList;
|
||||
import org.jetbrains.annotations.NotNull;
|
||||
import org.jetbrains.annotations.Nullable;
|
||||
|
||||
/**
|
||||
* This class represents all boss spawn events fired by EcoBosses.
|
||||
*/
|
||||
public class EcoBossSpawnEvent extends Event implements Cancellable {
|
||||
/**
|
||||
* Event cancellation state.
|
||||
*/
|
||||
private boolean cancelled;
|
||||
|
||||
/**
|
||||
* The boss to be spawned.
|
||||
*/
|
||||
private final EcoBoss boss;
|
||||
|
||||
/**
|
||||
* Location that boss will be spawned at.
|
||||
*/
|
||||
private final Location location;
|
||||
|
||||
/**
|
||||
* Player that spawned this boss.
|
||||
* (Will be null if EcoBossSpawnTimerEvent is fired)
|
||||
*/
|
||||
@Nullable
|
||||
private final Player player;
|
||||
|
||||
/**
|
||||
* Bukkit parity.
|
||||
*/
|
||||
private static final HandlerList HANDLERS = new HandlerList();
|
||||
|
||||
/**
|
||||
*
|
||||
* Default constructor
|
||||
*
|
||||
* @param boss - The boss to be spawned.
|
||||
* @param player - The player that spawned this boss (can be null)
|
||||
* @param location - The location that boss will spawn at.
|
||||
*/
|
||||
public EcoBossSpawnEvent(@NotNull final EcoBoss boss, @Nullable final Player player, @NotNull final Location location) {
|
||||
this.cancelled = false;
|
||||
this.boss = boss;
|
||||
this.location = location;
|
||||
this.player = player;
|
||||
}
|
||||
|
||||
/**
|
||||
*
|
||||
* Get the EcoBoss.
|
||||
*
|
||||
* @return - EcoBoss to be spawned.
|
||||
*/
|
||||
@NotNull
|
||||
public EcoBoss getBoss() {
|
||||
return this.boss;
|
||||
}
|
||||
|
||||
/**
|
||||
*
|
||||
* Get the location.
|
||||
*
|
||||
* @return - Location.
|
||||
*/
|
||||
@NotNull
|
||||
public Location getLocation() {
|
||||
return this.location;
|
||||
}
|
||||
|
||||
/**
|
||||
*
|
||||
* Get the player if present.
|
||||
*
|
||||
* @return - The player.
|
||||
*/
|
||||
@Nullable
|
||||
public Player getPlayer() {
|
||||
return this.player;
|
||||
}
|
||||
|
||||
/**
|
||||
*
|
||||
* Check if this event has any player presented.
|
||||
*
|
||||
* @return - If any player is presented in this event.
|
||||
*/
|
||||
public boolean hasPlayer() {
|
||||
return this.player != null;
|
||||
}
|
||||
|
||||
/**
|
||||
* Bukkit parity.
|
||||
*
|
||||
* @return The handlers.
|
||||
*/
|
||||
@Override
|
||||
public @NotNull HandlerList getHandlers() {
|
||||
return HANDLERS;
|
||||
}
|
||||
|
||||
/**
|
||||
*
|
||||
* Get if event is cancelled.
|
||||
*
|
||||
* @return Event cancellation state.
|
||||
*/
|
||||
@Override
|
||||
public boolean isCancelled() {
|
||||
return this.cancelled;
|
||||
}
|
||||
|
||||
/**
|
||||
*
|
||||
* Set event cancellation state.
|
||||
*
|
||||
* @param b - The state to set.
|
||||
*/
|
||||
@Override
|
||||
public void setCancelled(boolean b) {
|
||||
this.cancelled = b;
|
||||
}
|
||||
|
||||
/**
|
||||
* Bukkit parity.
|
||||
*
|
||||
* @return The handler list.
|
||||
*/
|
||||
public static HandlerList getHandlerList() {
|
||||
return HANDLERS;
|
||||
}
|
||||
}
|
||||
@@ -0,0 +1,42 @@
|
||||
package com.willfp.ecobosses.events;
|
||||
|
||||
import com.willfp.ecobosses.bosses.EcoBoss;
|
||||
import org.bukkit.Location;
|
||||
import org.bukkit.event.HandlerList;
|
||||
import org.jetbrains.annotations.NotNull;
|
||||
|
||||
public class EcoBossSpawnTimerEvent extends EcoBossSpawnEvent {
|
||||
/**
|
||||
* Bukkit parity.
|
||||
*/
|
||||
private static final HandlerList HANDLERS = new HandlerList();
|
||||
|
||||
/**
|
||||
* Default constructor
|
||||
*
|
||||
* @param boss - The boss to be spawned.
|
||||
* @param location - The location that boss will spawn at.
|
||||
*/
|
||||
public EcoBossSpawnTimerEvent(@NotNull EcoBoss boss, @NotNull Location location) {
|
||||
super(boss, null, location);
|
||||
}
|
||||
|
||||
/**
|
||||
* Bukkit parity.
|
||||
*
|
||||
* @return The handlers.
|
||||
*/
|
||||
@Override
|
||||
public @NotNull HandlerList getHandlers() {
|
||||
return HANDLERS;
|
||||
}
|
||||
|
||||
/**
|
||||
* Bukkit parity.
|
||||
*
|
||||
* @return The handler list.
|
||||
*/
|
||||
public static HandlerList getHandlerList() {
|
||||
return HANDLERS;
|
||||
}
|
||||
}
|
||||
@@ -0,0 +1,59 @@
|
||||
package com.willfp.ecobosses.events;
|
||||
|
||||
import com.willfp.ecobosses.bosses.EcoBoss;
|
||||
import com.willfp.ecobosses.bosses.util.obj.SpawnTotem;
|
||||
import org.bukkit.Location;
|
||||
import org.bukkit.entity.Player;
|
||||
import org.bukkit.event.HandlerList;
|
||||
import org.jetbrains.annotations.NotNull;
|
||||
import org.jetbrains.annotations.Nullable;
|
||||
|
||||
public class EcoBossSpawnTotemEvent extends EcoBossSpawnEvent {
|
||||
/**
|
||||
* The totem.
|
||||
*/
|
||||
@NotNull
|
||||
private final SpawnTotem totem;
|
||||
|
||||
/**
|
||||
* Bukkit parity.
|
||||
*/
|
||||
private static final HandlerList HANDLERS = new HandlerList();
|
||||
|
||||
/**
|
||||
* Default constructor
|
||||
*
|
||||
* @param boss - The boss to be spawned.
|
||||
* @param player - The player that spawned this boss (can be null)
|
||||
* @param location - The location that boss will spawn at.
|
||||
* @param totem - The totem.
|
||||
*/
|
||||
public EcoBossSpawnTotemEvent(@NotNull final EcoBoss boss, @Nullable final Player player, @NotNull final Location location, @NotNull final SpawnTotem totem) {
|
||||
super(boss, player, location);
|
||||
this.totem = totem;
|
||||
}
|
||||
|
||||
@NotNull
|
||||
public SpawnTotem getTotem() {
|
||||
return this.totem;
|
||||
}
|
||||
|
||||
/**
|
||||
* Bukkit parity.
|
||||
*
|
||||
* @return The handlers.
|
||||
*/
|
||||
@Override
|
||||
public @NotNull HandlerList getHandlers() {
|
||||
return HANDLERS;
|
||||
}
|
||||
|
||||
/**
|
||||
* Bukkit parity.
|
||||
*
|
||||
* @return The handler list.
|
||||
*/
|
||||
public static HandlerList getHandlerList() {
|
||||
return HANDLERS;
|
||||
}
|
||||
}
|
||||
@@ -0,0 +1,24 @@
|
||||
package com.willfp.ecobosses.integrations.levelledmobs;
|
||||
|
||||
import com.willfp.ecobosses.bosses.EcoBoss;
|
||||
import com.willfp.ecobosses.bosses.util.BossUtils;
|
||||
import me.lokka30.levelledmobs.events.MobPreLevelEvent;
|
||||
import org.bukkit.entity.Boat;
|
||||
import org.bukkit.entity.LivingEntity;
|
||||
import org.bukkit.entity.Minecart;
|
||||
import org.bukkit.event.EventHandler;
|
||||
import org.bukkit.event.Listener;
|
||||
import org.jetbrains.annotations.NotNull;
|
||||
|
||||
public class LevelledMobsListener implements Listener {
|
||||
@EventHandler
|
||||
public void onMobLevel(@NotNull final MobPreLevelEvent event) {
|
||||
EcoBoss boss = BossUtils.getBoss(event.getEntity());
|
||||
|
||||
if (boss == null) {
|
||||
return;
|
||||
}
|
||||
|
||||
event.setCancelled(true);
|
||||
}
|
||||
}
|
||||
@@ -0,0 +1,46 @@
|
||||
package com.willfp.ecobosses.util;
|
||||
|
||||
import com.willfp.eco.core.EcoPlugin;
|
||||
import com.willfp.eco.core.PluginDependent;
|
||||
import org.bukkit.Bukkit;
|
||||
import org.bukkit.NamespacedKey;
|
||||
import org.bukkit.entity.Player;
|
||||
import org.bukkit.event.EventHandler;
|
||||
import org.bukkit.event.Listener;
|
||||
import org.bukkit.event.player.PlayerJoinEvent;
|
||||
import org.bukkit.inventory.ShapedRecipe;
|
||||
import org.jetbrains.annotations.NotNull;
|
||||
|
||||
public class DiscoverRecipeListener extends PluginDependent<EcoPlugin> implements Listener {
|
||||
/**
|
||||
* Register listener.
|
||||
*
|
||||
* @param plugin Talismans.
|
||||
*/
|
||||
public DiscoverRecipeListener(@NotNull final EcoPlugin plugin) {
|
||||
super(plugin);
|
||||
}
|
||||
|
||||
/**
|
||||
* Unlock all recipes on player join.
|
||||
*
|
||||
* @param event The event to listen for.
|
||||
*/
|
||||
@EventHandler
|
||||
public void onJoin(@NotNull final PlayerJoinEvent event) {
|
||||
Player player = event.getPlayer();
|
||||
|
||||
if (this.getPlugin().getConfigYml().getBool("discover-recipes")) {
|
||||
Bukkit.getServer().recipeIterator().forEachRemaining(recipe -> {
|
||||
if (recipe instanceof ShapedRecipe) {
|
||||
NamespacedKey key = ((ShapedRecipe) recipe).getKey();
|
||||
if (key.getNamespace().equals("ecobosses")) {
|
||||
if (!key.getKey().contains("displayed")) {
|
||||
player.discoverRecipe(key);
|
||||
}
|
||||
}
|
||||
}
|
||||
});
|
||||
}
|
||||
}
|
||||
}
|
||||
@@ -1,7 +1,8 @@
|
||||
enabled: true
|
||||
|
||||
name: "&fAlpha Wolf &7| &c%health%♥" # Display name
|
||||
base-mob: wolf # Any existing mob - custom_illusioner is also accepted (like in the old Illusioner plugin)
|
||||
name: "&fAlpha Wolf &7| &c%health%♥ &7| &e%time%" # Display name
|
||||
base-mob: wolf
|
||||
baby: false # If set to true: will make the boss mob baby (if possible)
|
||||
|
||||
bossbar:
|
||||
enabled: true
|
||||
@@ -12,12 +13,37 @@ max-health: 600
|
||||
attack-damage: 50
|
||||
movement-speed: 2
|
||||
follow-range: 15
|
||||
time-to-live: 120 # Time to live before auto despawn, in seconds. Set to -1 to disable.
|
||||
glowing: false # Should this boss have glowing effect
|
||||
|
||||
auto-spawn-interval: -1 # Time between auto spawns in ticks (20 ticks in a second) - Set to -1 to disable.
|
||||
auto-spawn-locations: [ ] # Formatted as world:x:y:z - for example world_nether:100:10:100
|
||||
|
||||
spawn-totem:
|
||||
spawn-requirements: []
|
||||
|
||||
spawn-egg:
|
||||
enabled: true
|
||||
material: wolf_spawn_egg
|
||||
name: "&fAlpha Wolf Spawn Egg"
|
||||
lore:
|
||||
- ""
|
||||
- "&8&oPlace on the ground to"
|
||||
- "&8&osummon an &fAlpha Wolf"
|
||||
glow: true
|
||||
craftable: true
|
||||
recipe:
|
||||
- bone_block
|
||||
- netherite_block
|
||||
- bone_block
|
||||
- bone
|
||||
- ecoitems:boss_core ? nether_star
|
||||
- bone
|
||||
- bone_block
|
||||
- netherite_block
|
||||
- bone_block
|
||||
|
||||
spawn-totem:
|
||||
enabled: false
|
||||
top: beacon
|
||||
middle: bone_block
|
||||
bottom: bone_block
|
||||
@@ -38,8 +64,7 @@ rewards:
|
||||
# Use %player% as the placeholder for the player name
|
||||
commands: []
|
||||
|
||||
# Get items to add here by copying the console output for /ecobosses base64
|
||||
# To set the chance for a drop, put <chance>::<base64>
|
||||
# To set the chance for a drop, put <chance>::item
|
||||
drops: []
|
||||
|
||||
broadcast:
|
||||
@@ -56,6 +81,10 @@ broadcast:
|
||||
- "&f - %second%&f (%second_damage% Damage)"
|
||||
- "&f - %third%&f (%third_damage% Damage)"
|
||||
- ""
|
||||
despawn:
|
||||
- ""
|
||||
- "&fYou ran out of time to kill the &lAlpha Wolf&r&f!"
|
||||
- ""
|
||||
|
||||
# Effects can be found on the wiki! https://ecobosses.willfp.com/
|
||||
effects:
|
||||
@@ -63,6 +92,23 @@ effects:
|
||||
- "give-potion-effect:wither:4:200:10"
|
||||
- "give-potion-effect:hunger:10:600:10"
|
||||
|
||||
gear:
|
||||
helmet:
|
||||
item: ""
|
||||
chance: 100
|
||||
chestplate:
|
||||
item: ""
|
||||
chance: 100
|
||||
leggings:
|
||||
item: ""
|
||||
chance: 100
|
||||
boots:
|
||||
item: ""
|
||||
chance: 100
|
||||
hand:
|
||||
item: ""
|
||||
chance: 100
|
||||
|
||||
defence:
|
||||
immunities:
|
||||
explosion: false
|
||||
@@ -104,6 +150,10 @@ sounds:
|
||||
- "entity_wolf_death:50:0.7"
|
||||
- "entity_wolf_growl:50:0.8"
|
||||
|
||||
despawn:
|
||||
- "entity_ender_dragon_ambient:50:0.5"
|
||||
- "entity_enderman_death:50:0.5"
|
||||
|
||||
summon: # On summon enemy
|
||||
- "entity_wolf_pant:10:0.8"
|
||||
|
||||
|
||||
@@ -1,7 +1,8 @@
|
||||
enabled: true
|
||||
|
||||
name: "&9Illusioner &7| &c%health%♥" # Display name
|
||||
base-mob: custom_illusioner # Any existing mob - custom_illusioner is also accepted (like in the old Illusioner plugin)
|
||||
name: "&9Dark Guardian &7| &c%health%♥ &7| &e%time%" # Display name
|
||||
base-mob: ravager
|
||||
baby: false # If set to true: will make the boss mob baby (if possible)
|
||||
|
||||
bossbar:
|
||||
enabled: true
|
||||
@@ -12,12 +13,37 @@ max-health: 300
|
||||
attack-damage: 30
|
||||
movement-speed: 1.2
|
||||
follow-range: 20
|
||||
time-to-live: 120 # Time to live before auto despawn, in seconds. Set to -1 to disable.
|
||||
glowing: false # Should this boss have glowing effect
|
||||
|
||||
auto-spawn-interval: -1 # Time between auto spawns in ticks (20 ticks in a second) - Set to -1 to disable.
|
||||
auto-spawn-locations: [ ] # Formatted as world:x:y:z - for example world_nether:100:10:100
|
||||
|
||||
spawn-totem:
|
||||
spawn-requirements: []
|
||||
|
||||
spawn-egg:
|
||||
enabled: true
|
||||
material: ravager_spawn_egg
|
||||
name: "&9Dark Guardian&f Spawn Egg"
|
||||
lore:
|
||||
- ""
|
||||
- "&8&oPlace on the ground to"
|
||||
- "&8&osummon a &9Dark Guardian"
|
||||
glow: true
|
||||
craftable: true
|
||||
recipe:
|
||||
- emerald
|
||||
- netherite_block
|
||||
- emerald
|
||||
- air
|
||||
- ecoitems:boss_core ? nether_star
|
||||
- air
|
||||
- emerald
|
||||
- netherite_block
|
||||
- emerald
|
||||
|
||||
spawn-totem:
|
||||
enabled: false
|
||||
top: carved_pumpkin
|
||||
middle: beacon
|
||||
bottom: diamond_block
|
||||
@@ -38,34 +64,54 @@ rewards:
|
||||
# Use %player% as the placeholder for the player name
|
||||
commands: []
|
||||
|
||||
# Get items to add here by copying the console output for /ecobosses base64
|
||||
# To set the chance for a drop, put <chance>::<base64>
|
||||
# To set the chance for a drop, put <chance>::item
|
||||
drops: []
|
||||
|
||||
broadcast:
|
||||
spawn:
|
||||
- ""
|
||||
- "&fAn &9&lIllusioner&r&f has been spawned!"
|
||||
- "&fA &9&lDark Guardian&r&f has been spawned!"
|
||||
- "&fCome fight it at &9%x%&f, &9%y%&f, &9%z%&f!"
|
||||
- ""
|
||||
death:
|
||||
- ""
|
||||
- "&fThe &9&lIllusioner&r&f has been killed!"
|
||||
- "&fThe &9&lDark Guardian&r&f has been killed!"
|
||||
- "&fMost Damage:"
|
||||
- "&f - &9%top%&f (%top_damage% Damage)"
|
||||
- "&f - &9%second%&f (%second_damage% Damage)"
|
||||
- "&f - &9%third%&f (%third_damage% Damage)"
|
||||
- ""
|
||||
despawn:
|
||||
- ""
|
||||
- "&fYou ran out of time to kill the &9&lDark Guardian&r&f!"
|
||||
- ""
|
||||
|
||||
# Effects can be found on the wiki! https://ecobosses.willfp.com/
|
||||
effects:
|
||||
- "summon:evoker:10"
|
||||
- "summon:vindicator:10"
|
||||
- "summon:enderman:10"
|
||||
- "shuffle-hotbar:10"
|
||||
- "give-potion-effect:confusion:10:200:10"
|
||||
- "give-potion-effect:blindness:1:40:20"
|
||||
- "teleport:7:15"
|
||||
|
||||
gear:
|
||||
helmet:
|
||||
item: ""
|
||||
chance: 100
|
||||
chestplate:
|
||||
item: ""
|
||||
chance: 100
|
||||
leggings:
|
||||
item: ""
|
||||
chance: 100
|
||||
boots:
|
||||
item: ""
|
||||
chance: 100
|
||||
hand:
|
||||
item: ""
|
||||
chance: 100
|
||||
|
||||
defence:
|
||||
immunities:
|
||||
explosion: true
|
||||
@@ -102,11 +148,17 @@ sounds:
|
||||
spawn: # On spawn
|
||||
- "entity_illusioner_mirror_move:100:0.5"
|
||||
- "entity_wither_spawn:100:2"
|
||||
- "entity_enderman_death:50:2"
|
||||
|
||||
death: # On death
|
||||
- "entity_evoker_prepare_wololo:50:0.8"
|
||||
- "entity_illusioner_prepare_blindness:50:1"
|
||||
- "entity_wither_death:50:2"
|
||||
- "entity_enderman_death:50:0.5"
|
||||
|
||||
despawn:
|
||||
- "entity_ender_dragon_ambient:50:0.5"
|
||||
- "entity_enderman_death:50:0.5"
|
||||
|
||||
summon: # On summon enemy
|
||||
- "entity_evoker_prepare_attack:10:2"
|
||||
@@ -1,7 +1,8 @@
|
||||
enabled: true
|
||||
|
||||
name: "&8Steel Golem &7| &c%health%♥" # Display name
|
||||
base-mob: iron_golem # Any existing mob - custom_illusioner is also accepted (like in the old Illusioner plugin)
|
||||
name: "&8Steel Golem &7| &c%health%♥ &7| &e%time%" # Display name
|
||||
base-mob: iron_golem
|
||||
baby: false # If set to true: will make the boss mob baby (if possible)
|
||||
|
||||
bossbar:
|
||||
enabled: true
|
||||
@@ -12,12 +13,37 @@ max-health: 1200
|
||||
attack-damage: 90
|
||||
movement-speed: 1.5
|
||||
follow-range: 16
|
||||
time-to-live: 120 # Time to live before auto despawn, in seconds. Set to -1 to disable.
|
||||
glowing: false # Should this boss have glowing effect
|
||||
|
||||
auto-spawn-interval: -1 # Time between auto spawns in ticks (20 ticks in a second) - Set to -1 to disable.
|
||||
auto-spawn-locations: [] # Formatted as world:x:y:z - for example world_nether:100:10:100
|
||||
|
||||
spawn-totem:
|
||||
spawn-requirements: []
|
||||
|
||||
spawn-egg:
|
||||
enabled: true
|
||||
material: evoker_spawn_egg
|
||||
name: "&8Steel Golem&f Spawn Egg"
|
||||
lore:
|
||||
- ""
|
||||
- "&8&oPlace on the ground to"
|
||||
- "&8&osummon a &8Steel Golem"
|
||||
glow: true
|
||||
craftable: true
|
||||
recipe:
|
||||
- iron_block
|
||||
- netherite_block
|
||||
- iron_block
|
||||
- air
|
||||
- ecoitems:boss_core ? nether_star
|
||||
- air
|
||||
- iron_block
|
||||
- netherite_block
|
||||
- iron_block
|
||||
|
||||
spawn-totem:
|
||||
enabled: false
|
||||
top: netherite_block
|
||||
middle: iron_block
|
||||
bottom: magma_block
|
||||
@@ -38,8 +64,7 @@ rewards:
|
||||
# Use %player% as the placeholder for the player name
|
||||
commands: []
|
||||
|
||||
# Get items to add here by copying the console output for /ecobosses base64
|
||||
# To set the chance for a drop, put <chance>::<base64>
|
||||
# To set the chance for a drop, put <chance>::item
|
||||
drops: []
|
||||
|
||||
broadcast:
|
||||
@@ -56,6 +81,10 @@ broadcast:
|
||||
- "&f - &8%second%&f (%second_damage% Damage)"
|
||||
- "&f - &8%third%&f (%third_damage% Damage)"
|
||||
- ""
|
||||
despawn:
|
||||
- ""
|
||||
- "&fYou ran out of time to kill the &8&lSteel Golem&r&f!"
|
||||
- ""
|
||||
|
||||
# Effects can be found on the wiki! https://ecobosses.willfp.com/
|
||||
effects:
|
||||
@@ -67,6 +96,23 @@ effects:
|
||||
- "give-potion-effect:slow:5:100:20"
|
||||
- "give-potion-effect:levitation:3:50:10"
|
||||
|
||||
gear:
|
||||
helmet:
|
||||
item: ""
|
||||
chance: 100
|
||||
chestplate:
|
||||
item: ""
|
||||
chance: 100
|
||||
leggings:
|
||||
item: ""
|
||||
chance: 100
|
||||
boots:
|
||||
item: ""
|
||||
chance: 100
|
||||
hand:
|
||||
item: ""
|
||||
chance: 100
|
||||
|
||||
defence:
|
||||
immunities:
|
||||
explosion: true
|
||||
@@ -109,6 +155,10 @@ sounds:
|
||||
- "entity_ender_dragon_death:50:1.8"
|
||||
- "entity_wither_death:50:1.2"
|
||||
|
||||
despawn:
|
||||
- "entity_ender_dragon_ambient:50:0.5"
|
||||
- "entity_enderman_death:50:0.5"
|
||||
|
||||
summon: # On summon enemy
|
||||
- "entity_iron_golem_step:10:1.2"
|
||||
|
||||
|
||||
@@ -1,7 +1,8 @@
|
||||
enabled: true
|
||||
|
||||
name: "&4Tarantula &7| &c%health%♥" # Display name
|
||||
base-mob: cave_spider # Any existing mob - custom_illusioner is also accepted (like in the old Illusioner plugin)
|
||||
name: "&4Tarantula &7| &c%health%♥ &7| &e%time%" # Display name
|
||||
base-mob: cave_spider
|
||||
baby: false # If set to true: will make the boss mob baby (if possible)
|
||||
|
||||
bossbar:
|
||||
enabled: true
|
||||
@@ -12,12 +13,37 @@ max-health: 900
|
||||
attack-damage: 70
|
||||
movement-speed: 1.3
|
||||
follow-range: 15
|
||||
time-to-live: 120 # Time to live before auto despawn, in seconds. Set to -1 to disable.
|
||||
glowing: false # Should this boss have glowing effect
|
||||
|
||||
auto-spawn-interval: -1 # Time between auto spawns in ticks (20 ticks in a second) - Set to -1 to disable.
|
||||
auto-spawn-locations: [ ] # Formatted as world:x:y:z - for example world_nether:100:10:100
|
||||
|
||||
spawn-totem:
|
||||
spawn-requirements: []
|
||||
|
||||
spawn-egg:
|
||||
enabled: true
|
||||
material: cave_spider_spawn_egg
|
||||
name: "&4Tarantula&f Spawn Egg"
|
||||
lore:
|
||||
- ""
|
||||
- "&8&oPlace on the ground to"
|
||||
- "&8&osummon a &4Tarantula"
|
||||
glow: true
|
||||
craftable: true
|
||||
recipe:
|
||||
- string
|
||||
- netherite_block
|
||||
- string
|
||||
- air
|
||||
- ecoitems:boss_core ? nether_star
|
||||
- air
|
||||
- string
|
||||
- netherite_block
|
||||
- string
|
||||
|
||||
spawn-totem:
|
||||
enabled: false
|
||||
top: netherite_block
|
||||
middle: red_wool
|
||||
bottom: white_wool
|
||||
@@ -38,8 +64,7 @@ rewards:
|
||||
# Use %player% as the placeholder for the player name
|
||||
commands: []
|
||||
|
||||
# Get items to add here by copying the console output for /ecobosses base64
|
||||
# To set the chance for a drop, put <chance>::<base64>
|
||||
# To set the chance for a drop, put <chance>::item
|
||||
drops: []
|
||||
|
||||
broadcast:
|
||||
@@ -56,6 +81,10 @@ broadcast:
|
||||
- "&f - &4%second%&f (%second_damage% Damage)"
|
||||
- "&f - &4%third%&f (%third_damage% Damage)"
|
||||
- ""
|
||||
despawn:
|
||||
- ""
|
||||
- "&fYou ran out of time to kill the &4&lTarantula&r&f!"
|
||||
- ""
|
||||
|
||||
# Effects can be found on the wiki! https://ecobosses.willfp.com/
|
||||
effects:
|
||||
@@ -67,6 +96,23 @@ effects:
|
||||
- "give-potion-effect:hunger:5:400:10"
|
||||
- "give-potion-effect:slow_digging:3:40:10"
|
||||
|
||||
gear:
|
||||
helmet:
|
||||
item: ""
|
||||
chance: 100
|
||||
chestplate:
|
||||
item: ""
|
||||
chance: 100
|
||||
leggings:
|
||||
item: ""
|
||||
chance: 100
|
||||
boots:
|
||||
item: ""
|
||||
chance: 100
|
||||
hand:
|
||||
item: ""
|
||||
chance: 100
|
||||
|
||||
defence:
|
||||
immunities:
|
||||
explosion: false
|
||||
@@ -108,6 +154,10 @@ sounds:
|
||||
- "entity_spider_death:50:0.7"
|
||||
- "entity_wither_death:50:0.5"
|
||||
|
||||
despawn:
|
||||
- "entity_ender_dragon_ambient:50:0.5"
|
||||
- "entity_enderman_death:50:0.5"
|
||||
|
||||
summon: # On summon enemy
|
||||
- "entity_spider_step:10:1.2"
|
||||
|
||||
|
||||
@@ -4,5 +4,6 @@
|
||||
#
|
||||
|
||||
bossbar-radius: 50 # How far away players should be able to see the boss bar for bosses.
|
||||
discover-recipes: true
|
||||
|
||||
# Read the wiki! https://ecobosses.willfp.com/
|
||||
@@ -9,5 +9,11 @@ messages:
|
||||
invalid-location: "&cInvalid location!"
|
||||
spawned: "Spawned a boss!"
|
||||
killall: "Killed &a%amount%&f bosses!"
|
||||
needs-player: "&cYou must specify a player"
|
||||
invalid-player: "&cInvalid player!"
|
||||
needs-stone: "&cYou must specify a boss"
|
||||
invalid-stone: "&cInvalid boss!"
|
||||
give-success: "Gave &a%boss%&r spawn egg to &a%recipient%"
|
||||
requirements-not-met: "&cYou can't spawn this boss!"
|
||||
|
||||
na: "N/A"
|
||||
@@ -5,6 +5,9 @@ api-version: 1.16
|
||||
authors: [Auxilor]
|
||||
website: willfp.com
|
||||
load: STARTUP
|
||||
softdepend:
|
||||
- MythicMobs
|
||||
- LevelledMobs
|
||||
depend:
|
||||
- eco
|
||||
|
||||
@@ -26,14 +29,14 @@ permissions:
|
||||
ecobosses.command.ecobosses: true
|
||||
ecobosses.command.reload: true
|
||||
ecobosses.command.spawn: true
|
||||
ecobosses.command.base64: true
|
||||
ecobosses.command.give: true
|
||||
|
||||
ecobosses.command.ecobosses:
|
||||
description: Allows the use of /ecobosses
|
||||
default: true
|
||||
|
||||
ecobosses.command.base64:
|
||||
description: Allows the use of /ecobosses base64
|
||||
ecobosses.command.give:
|
||||
description: Allows the use of /ecobosses give
|
||||
default: op
|
||||
|
||||
ecobosses.command.spawn:
|
||||
|
||||
@@ -1,6 +0,0 @@
|
||||
group 'com.willfp'
|
||||
version rootProject.version
|
||||
|
||||
dependencies {
|
||||
compileOnly 'org.spigotmc:spigot-api:1.16.4-R0.1-SNAPSHOT'
|
||||
}
|
||||
@@ -1,21 +0,0 @@
|
||||
package com.willfp.ecobosses.proxy.proxies;
|
||||
|
||||
import com.willfp.eco.core.proxy.AbstractProxy;
|
||||
import com.willfp.ecobosses.proxy.util.CustomEntity;
|
||||
import org.bukkit.Location;
|
||||
import org.bukkit.entity.LivingEntity;
|
||||
import org.jetbrains.annotations.NotNull;
|
||||
import org.jetbrains.annotations.Nullable;
|
||||
|
||||
public interface CustomEntitySpawnerProxy extends AbstractProxy {
|
||||
/**
|
||||
* Spawn custom entity.
|
||||
*
|
||||
* @param <T> The class.
|
||||
* @param entityClass The custom entity proxy class.
|
||||
* @param location The location.
|
||||
* @return The bukkit entity, or null if invalid class.
|
||||
*/
|
||||
@Nullable <T extends LivingEntity> T spawnCustomEntity(Class<? extends CustomEntity<? extends LivingEntity>> entityClass,
|
||||
@NotNull Location location);
|
||||
}
|
||||
@@ -1,9 +0,0 @@
|
||||
package com.willfp.ecobosses.proxy.proxies;
|
||||
|
||||
import com.willfp.eco.core.proxy.AbstractProxy;
|
||||
import com.willfp.ecobosses.proxy.util.CustomEntity;
|
||||
import org.bukkit.entity.Illusioner;
|
||||
|
||||
public interface CustomIllusionerProxy extends AbstractProxy, CustomEntity<Illusioner> {
|
||||
|
||||
}
|
||||
@@ -1,30 +0,0 @@
|
||||
package com.willfp.ecobosses.proxy.util;
|
||||
|
||||
import com.google.common.collect.BiMap;
|
||||
import com.google.common.collect.ImmutableBiMap;
|
||||
import com.willfp.ecobosses.proxy.proxies.CustomIllusionerProxy;
|
||||
import lombok.experimental.UtilityClass;
|
||||
import org.bukkit.entity.LivingEntity;
|
||||
import org.jetbrains.annotations.NotNull;
|
||||
import org.jetbrains.annotations.Nullable;
|
||||
|
||||
@UtilityClass
|
||||
public class CustomEntities {
|
||||
/**
|
||||
* Registered custom entities.
|
||||
*/
|
||||
private static final BiMap<String, Class<? extends CustomEntity<? extends LivingEntity>>> REGISTRY = new ImmutableBiMap.Builder<String, Class<? extends CustomEntity<? extends LivingEntity>>>()
|
||||
.put("custom_illusioner", CustomIllusionerProxy.class)
|
||||
.build();
|
||||
|
||||
/**
|
||||
* Get entity class.
|
||||
*
|
||||
* @param id The entity id.
|
||||
* @return The class.
|
||||
*/
|
||||
@Nullable
|
||||
public Class<? extends CustomEntity<? extends LivingEntity>> getEntityClass(@NotNull final String id) {
|
||||
return REGISTRY.get(id);
|
||||
}
|
||||
}
|
||||
@@ -1,7 +0,0 @@
|
||||
package com.willfp.ecobosses.proxy.util;
|
||||
|
||||
import org.bukkit.entity.LivingEntity;
|
||||
|
||||
public interface CustomEntity<T extends LivingEntity> {
|
||||
|
||||
}
|
||||
@@ -1,2 +1,2 @@
|
||||
version = 6.0.0
|
||||
version = 6.8.0
|
||||
plugin-name = EcoBosses
|
||||
@@ -1,11 +1,12 @@
|
||||
pluginManagement {
|
||||
repositories {
|
||||
gradlePluginPortal()
|
||||
maven { url "https://repo.jpenilla.xyz/snapshots/" }
|
||||
}
|
||||
}
|
||||
|
||||
rootProject.name = 'EcoBosses'
|
||||
|
||||
// Core
|
||||
include ':eco-core'
|
||||
include ':eco-core:core-nms'
|
||||
include ':eco-core:core-nms:v1_16_R1'
|
||||
include ':eco-core:core-nms:v1_16_R2'
|
||||
include ':eco-core:core-nms:v1_16_R3'
|
||||
include ':eco-core:core-nms:v1_17_R1'
|
||||
include ':eco-core:core-proxy'
|
||||
include ':eco-core:core-plugin'
|
||||
Reference in New Issue
Block a user