///
///
import Feature from "../../featureClass/class";
import { f, m } from "../../../mappings/mappings";
import { numberWithCommas } from "../../utils/numberUtils";
import { drawBoxAtBlock, drawBoxAtEntity, drawFilledBox, drawLine } from "../../utils/renderUtils";
import HudTextElement from "../hud/HudTextElement";
import LocationSetting from "../settings/settingThings/location";
import ToggleSetting from "../settings/settingThings/toggle";
class Slayers extends Feature {
constructor() {
super()
}
onEnable(){
this.initVariables()
this.expOnKill = new ToggleSetting("Show slayer exp on boss kill", "Says your slayer exp in chat when you kill a boss, also says time taken to spawn+kill", true, "slayer_xp", this)
this.slainAlert = new ToggleSetting("Show boss slain alert", "This helps you to not kill mobs for ages with an inactive quest", true, "boss_slain_alert", this)
this.spawnAlert = new ToggleSetting("Show boss spawned alert", "This helps you to not miss your boss when you spawn it", true, "boss_spawn_alert", this)
this.boxAroundEmanBoss = new ToggleSetting("Box around enderman slayer boss", "This helps to know what boss it yours", true, "eman_box", this)
this.boxToEmanBeacon = new ToggleSetting("Box and line to the enderman beacon", "This will help to find the beacon when the boss throws it", true, "eman_beacon", this)
this.emanBeaconDinkDonk = new ToggleSetting("DinkDonk when beacon is spawned", "This will help to notice when the beacon is spawned", true, "eman_beacon_dinkdink", this)
this.emanEyeThings = new ToggleSetting("Put box around the enderman eye things", "This will help to find them", true, "eman_eye_thing", this)
this.emanHpGuiElement = new ToggleSetting("Render the enderman hp on your screen", "This will help you to know what stage u are in ect", true, "eman_hp", this)
this.emanHpElement = new HudTextElement()
.setToggleSetting(this.emanHpGuiElement)
.setLocationSetting(new LocationSetting("Eman Hp Location", "Allows you to edit the location of the enderman hp", "eman_location", this, [10, 50, 1, 1])
.requires(this.emanHpGuiElement)
.editTempText("&6Enderman&7> &f&l30 Hits"))
this.hudElements.push(this.emanHpElement)
this.slayerExp = {}
this.slayerExpLoaded = false
this.lastSlayerType = ""
this.lastSlayerExp = 0
this.lastBossSlain = 0
this.registerChat("&r &r&a&lSLAYER QUEST COMPLETE!&r",(e)=>{
this.slayerExp[this.lastSlayerType] = this.lastSlayerExp + (this.slayerExp[this.lastSlayerType] || 0)
if(this.expOnKill.getValue()){
cancel(e)
ChatLib.chat("&r &r&a&lSLAYER QUEST COMPLETE!&r")
ChatLib.chat("&r &r&aYou have &d" + numberWithCommas(this.slayerExp[this.lastSlayerType]) + " " + this.lastSlayerType + " XP&r&7!&r")
ChatLib.chat("&r &r&aYou have &d" + numberWithCommas(Object.values(this.slayerExp).reduce((a, t)=>t+a, 0)) + " total XP&r&7!&r")
if(Date.now()-this.lastBossSlain < 60000*5) ChatLib.chat("&r &r&aBoss took &d" + timeNumber((Date.now()-this.lastBossSlain)) + " &ato spawn and kill&r&7!"+/* (" + timeNumber(Date.now()-this.lastBossSpawned) + " to kill) */"&r") //TODO: Seperate setting for this
}
this.lastBossSlain = Date.now()
})
this.bossSlainMessage = false
this.bossSpawnedMessage = false
this.lastBossNotSpawnedTime = 0
this.lastBossSpawned = 0
this.registerEvent("renderOverlay", this.renderOverlay)
this.registerSoopy("apiLoad", this.apiLoad)
if(this.FeatureManager.features["dataLoader"].class.lastApiData.skyblock){
this.apiLoad(this.FeatureManager.features["dataLoader"].class.lastApiData.skyblock, "skyblock", true, true)
}
this.todoE = []
this.beaconPoints = {}
this.beaconE = []
this.deadE = []
this.beaconLocations = {}
this.eyeE = []
this.todoE2 = []
this.emanBoss = undefined
this.nextIsBoss = 0
this.counter = 0
this.entityAttackEventLoaded = false
this.entityAttackEventE = undefined
this.registerForge(net.minecraftforge.event.entity.EntityJoinWorldEvent, this.entityJoinWorldEvent)
this.registerEvent("tick", this.tick)
this.registerEvent("renderWorld", this.renderWorld)
this.registerEvent("worldLoad", this.worldLoad)
this.registerEvent("renderOverlay", this.renderHud)
}
renderHud(){
for(let element of this.hudElements){
element.render()
}
}
worldLoad(){
this.todoE = []
this.beaconPoints = {}
this.beaconE = []
this.deadE = []
this.todoE2 = []
this.beaconLocations = {}
this.eyeE = []
this.emanBoss = undefined
}
entityAttackEvent(event){
if(event.source.func_76346_g() === Player.getPlayer()){
if(event.entity instanceof net.minecraft.entity.monster.EntityEnderman){
World.getAllEntitiesOfType(net.minecraft.entity.item.EntityArmorStand).forEach(e=>{
if(e.getName().includes("Voidgloom Seraph")){
//if distance from e to event.entity < 5
if((e.getX() - event.entity[f.posX.Entity])**2 + (e.getY() - event.entity[f.posY.Entity])**2 + (e.getZ() - event.entity[f.posZ.Entity])**2 < 25){
this.emanBoss = e
}
}
})
}
}
}
renderWorld(ticks){
if(this.FeatureManager.features["dataLoader"].class.isInSkyblock){
if(!this.entityAttackEventLoaded){
this.entityAttackEventLoaded = true
this.entityAttackEventE = this.registerForge(net.minecraftforge.event.entity.living.LivingAttackEvent, this.entityAttackEvent) //TODO: Use CT event when ct 2.0 because they made the ct event actually work
}
}else{
if(this.entityAttackEventLoaded){
this.entityAttackEventLoaded = false
this.unregisterForge(this.entityAttackEventE)
}
}
Object.values(this.beaconPoints).forEach(line=>{
let lastPoint = undefined
line.forEach(p=>{
if(lastPoint){
drawLine(lastPoint[0], lastPoint[1], lastPoint[2], p[0], p[1], p[2], 0, 0, 255, 3)
}
lastPoint = p
})
})
this.eyeE.forEach(e=>{
let x = e.getX() + ((e.getX()-e.getLastX())*ticks)
let y = e.getY() + ((e.getY()-e.getLastY())*ticks)
let z = e.getZ() + ((e.getZ()-e.getLastZ())*ticks)
drawBoxAtBlock(x-0.5, y+0.7, z-0.5, 255, 0, 0)
})
if(this.emanBoss) drawBoxAtEntity(this.emanBoss, 0, 255, 0, 1, -3, ticks, 4, false)
Object.values(this.beaconLocations).forEach(loc=>{
drawFilledBox(loc[0]+0.5, loc[1], loc[2]+0.5, 1.01, 1.01, 0, 0, 1, 1, true)
})
}
entityJoinWorldEvent(event){
this.todoE2.push(event.entity)
}
tick(){
this.bossSlainMessage = false
let dis1 = false
Scoreboard.getLines().forEach((line, i) => {
if(ChatLib.removeFormatting(line.getName()).includes("Slayer Quest")){
let slayerInfo = ChatLib.removeFormatting(Scoreboard.getLines()[i-1].getName().replace(/§/g,"&"))
let levelString = slayerInfo.split(" ").pop().trim()
let slayerLevelToExp = {
"I": 5,
"II": 25,
"III": 100,
"IV": 500,
"V": 1500
}
this.lastSlayerExp = slayerLevelToExp[levelString]
let slayerStrToType = {
"revenant": "zombie",
"tarantula": "spider",
"sven": "wolf",
"voidgloom":"enderman"
}
this.lastSlayerType = slayerStrToType[slayerInfo.split(" ")[0].toLowerCase()]
//slayerExp[lastSlayerType] += lastSlayerExp
}
if (line.getName().includes('Boss slain!')) {
this.bossSlainMessage = true
}
if (line.getName().includes('Slay the boss!')) {
if(!this.bossSpawnedMessage && !this.emanBoss){
this.nextIsBoss = Date.now()
}
dis1 = true
this.bossSpawnedMessage = true
}
})
if (!dis1) {
this.lastBossNotSpawnedTime = Date.now()
this.bossSpawnedMessage = false
}
this.todoE.forEach(e=>{
try{
if(e instanceof net.minecraft.entity.item.EntityArmorStand && e[m.getEquipmentInSlot](4)){
if(e[m.getEquipmentInSlot](4)[m.getDisplayName.ItemStack]() === "Beacon"){
let closestEIsGaming = false
let closestDist = Infinity
World.getAllEntitiesOfType(net.minecraft.entity.item.EntityArmorStand).forEach(e2=>{
if(e2.getName().includes("Voidgloom Seraph")){
if((e2.getX() - e[f.posX.Entity])**2 + (e2.getY() - e[f.posY.Entity])**2 + (e2.getZ() - e[f.posZ.Entity])**2 < closestDist){
closestDist = (e2.getX() - e[f.posX.Entity])**2 + (e2.getY() - e[f.posY.Entity])**2 + (e2.getZ() - e[f.posZ.Entity])**2
closestEIsGaming = this.emanBoss?e2.getUUID().toString()===this.emanBoss.getUUID().toString():false
}
}
})
if(closestEIsGaming){
this.beaconE.push(e)
}
}
if(e[m.getEquipmentInSlot](4)[m.getDisplayName.ItemStack]().startsWith("§a")){
let closestEIsGaming = false
let closestDist = Infinity
World.getAllEntitiesOfType(net.minecraft.entity.item.EntityArmorStand).forEach(e2=>{
if(e2.getName().includes("Voidgloom Seraph")){
if((e2.getX() - e[f.posX.Entity])**2 + (e2.getY() - e[f.posY.Entity])**2 + (e2.getZ() - e[f.posZ.Entity])**2 < closestDist){
closestDist = (e2.getX() - e[f.posX.Entity])**2 + (e2.getY() - e[f.posY.Entity])**2 + (e2.getZ() - e[f.posZ.Entity])**2
closestEIsGaming = this.emanBoss?e2.getUUID().toString()===this.emanBoss.getUUID().toString():false
}
}
})
if(closestEIsGaming && new Item(e[m.getEquipmentInSlot](4)).getNBT().getCompoundTag("tag").getCompoundTag("SkullOwner").getCompoundTag("Properties").getRawNBT()[m.getTagList]("textures", 10)[m.getCompoundTagAt](0)[m.getString.NBTTagCompound]("Value") === "eyJ0ZXh0dXJlcyI6eyJTS0lOIjp7InVybCI6Imh0dHA6Ly90ZXh0dXJlcy5taW5lY3JhZnQubmV0L3RleHR1cmUvZWIwNzU5NGUyZGYyNzM5MjFhNzdjMTAxZDBiZmRmYTExMTVhYmVkNWI5YjIwMjllYjQ5NmNlYmE5YmRiYjRiMyJ9fX0="){
this.eyeE.push(new Entity(e))
}
// console.log(":" + new Item(e[m.getEquipmentInSlot](4)).getNBT().getCompoundTag("tag").getCompoundTag("SkullOwner").getCompoundTag("Properties").getRawNBT().func_150295_c("textures", 10).func_150305_b(0).func_74779_i("Value"))
}
}
if(e[m.getCustomNameTag]() && e[m.getCustomNameTag]().includes("Voidgloom Seraph")){
if(Date.now()-this.nextIsBoss < 3000){
this.emanBoss = new Entity(e)
this.nextIsBoss = false
}
}
}catch(_){console.log(JSON.stringify(_, undefined, 2))}
})
this.todoE = this.todoE2
this.todoE2 = []
if(this.emanBoss && this.emanBoss.getEntity()[f.isDead]) this.emanBoss = undefined
this.eyeE = this.eyeE.filter(e=>!e.getEntity()[f.isDead])
this.beaconE = this.beaconE.filter((e)=>{
if(e[f.isDead]){
this.deadE.push([Date.now(), e[m.getUniqueID.Entity]().toString()])
let pos = [e[f.posX.Entity]+0.5, e[f.posY.Entity]+0.7, e[f.posZ.Entity]+0.5]
//check for a beacon block within 5 blocks of pos
for(let x = pos[0] - 5; x <= pos[0] + 5; x++){
for(let y = pos[1] - 5; y <= pos[1] + 5; y++){
for(let z = pos[2] - 5; z <= pos[2] + 5; z++){
if(World.getBlockAt(Math.floor(x), Math.floor(y), Math.floor(z)).getID() === 138){
this.beaconLocations[e[m.getUniqueID.Entity]().toString()] = [Math.floor(x), Math.floor(y), Math.floor(z)]
}
}
}
}
// if(!this.beaconLocations[e[m.getUniqueID.Entity]().toString()]){
// console.log("Diddnt find beacon wtf?????")
// }
return false
}
return true
})
this.beaconE.forEach((e)=>{
if(!this.beaconPoints[e[m.getUniqueID.Entity]().toString()])this.beaconPoints[e[m.getUniqueID.Entity]().toString()] = []
this.beaconPoints[e[m.getUniqueID.Entity]().toString()].push([e[f.posX.Entity]+0.5, e[f.posY.Entity]+0.7, e[f.posZ.Entity]+0.5])//x, y, z
})
this.deadE = this.deadE.filter(e=>{
if(Date.now()-e[0] > 5000){
delete this.beaconPoints[e[1]]
delete this.beaconLocations[e[1]]
return false
}
let location = this.beaconLocations[e[1]]
if(!location){
delete this.beaconPoints[e[1]]
delete this.beaconLocations[e[1]]
return false
}
if(World.getBlockAt(location[0], location[1], location[2]).getID() === 138){
Client.showTitle("&cGO TO BEACON!","&c" + (Math.max(0,5000-(Date.now()-e[0]))/1000).toFixed(1) + "s",0,20,10)
World.playSound("note.pling",1,1)
}else{
delete this.beaconPoints[e[1]]
delete this.beaconLocations[e[1]]
return false
}
return true
})
if(this.emanBoss){
this.emanHpElement.setText("&6Enderman&7> " + this.emanBoss.getName().split("Voidgloom Seraph")[1].trim())
}else{
this.emanHpElement.setText("")
}
}
apiLoad(data, dataType, isSoopyServer, isLatest){
if(!isSoopyServer || !isLatest) return
if(dataType !== "skyblock") return
this.slayerExp.zombie = data.data.profiles[data.data.stats.currentProfileId].members[Player.getUUID().replace(/-/g, "")].slayer.zombie.xp
this.slayerExp.spider = data.data.profiles[data.data.stats.currentProfileId].members[Player.getUUID().replace(/-/g, "")].slayer.spider.xp
this.slayerExp.wolf = data.data.profiles[data.data.stats.currentProfileId].members[Player.getUUID().replace(/-/g, "")].slayer.wolf.xp
this.slayerExp.enderman = data.data.profiles[data.data.stats.currentProfileId].members[Player.getUUID().replace(/-/g, "")].slayer.enderman.xp
}
renderOverlay(){
if(this.slainAlert.getValue() && this.bossSlainMessage){
let scale = Renderer.getStringWidth(ChatLib.removeFormatting("BOSS SLAIN"))/(Renderer.screen.getWidth()*0.75)
Renderer.scale(1/scale, 1/scale)
Renderer.drawString("&4BOSS SLAIN", (Renderer.screen.getWidth()*0.125)*scale, (Renderer.screen.getHeight()/2-9/scale)*scale)
Renderer.scale(1, 1)
}
if(this.spawnAlert.getValue() && this.bossSpawnedMessage && Date.now()-this.lastBossNotSpawnedTime<3000){
let scale = Renderer.getStringWidth(ChatLib.removeFormatting("BOSS SPAWNED"))/(Renderer.screen.getWidth()*0.75)
Renderer.scale(1/scale, 1/scale)
Renderer.drawString("&4BOSS SPAWNED", (Renderer.screen.getWidth()*0.125)*scale, (Renderer.screen.getHeight()/2-9/scale)*scale)
Renderer.scale(1, 1)
}
}
initVariables(){
this.expOnKill = undefined
this.slainAlert = undefined
this.spawnAlert = undefined
this.slayerExp = undefined
this.slayerExpLoaded = undefined
this.lastSlayerType = undefined
this.lastSlayerExp = undefined
this.bossSpawnedMessage = undefined
this.lastBossNotSpawnedTime = undefined
this.bossSlainMessage = undefined
this.todoE = undefined
this.beaconPoints = undefined
this.beaconE = undefined
this.deadE = undefined
this.beaconLocations = undefined
this.emanBoss = undefined
this.eyeE = undefined
this.nextIsBoss = undefined
this.hudElements = []
this.entityAttackEventLoaded = undefined
this.todoE2 = undefined
this.entityAttackEventE = undefined
}
onDisable(){
this.initVariables()
}
}
module.exports = {
class: new Slayers()
}
function timeNumber(time){
let mins = Math.floor(time/1000/60)
let secs = Math.floor(time/1000)%60
if(mins === 0) return secs + "s"
return `${mins}m ${secs}s`
}