Untitled

mail@pastecode.io avatar
unknown
plain_text
a year ago
7.7 kB
6
Indexable
aura_env.happiness = aura_env.happiness or {}
aura_env.saved = aura_env.saved or {}
aura_env.saved.pets = aura_env.saved.pets or {}

local saved
local happiness = aura_env.happiness

local params = {
    debug = false,
    decayFactor = 1000/60,
    playerGUID = UnitGUID("player"),
    petContent = 1000/3,
    petHappy = 1000/3*2,
    bites = {
        [8.75]=true,
        [17.5]=true,
        [35]=true
    },
}

local function dPrint(...)
    if params.debug then
        print(...)
    end
end

local function check4Buff(buffId,unit)
    local unitAuraId
    for auraIndex = 1,100 do
        local unitAuras = {UnitAura(unit,1 , "HELPFUL")}
        unitAuraId = unitAuras[10]
        if not unitAuraId then
            return false
        elseif unitAuraId == buffId then
            return true
        end
    end
end

local function getDecay(loyalty)
    return params.decayFactor/(30+15*loyalty)
end

local function getLoyalty()
    local loyalty = GetPetLoyalty()
    return loyalty and tonumber(strsub(loyalty,16,16))
end

local function updateHappinessRank()
    local happinessRank = GetPetHappiness()
    if not happinessRank then
        return
    end
    local bite = check4Buff(1539,"pet") and 35 or 0
    if happinessRank > saved.happinessRank then
        if happinessRank == 3 and saved.happyLevel + bite < params.petHappy then
            saved.happyLevel = params.petHappy
        elseif happinessRank == 2 and saved.happyLevel + bite < params.petContent then
            saved.happyLevel = params.petContent
        end
    elseif happinessRank < saved.happinessRank then
        if happinessRank == 2 and (saved.happyLevel > params.petHappy or saved.happyLevel < params.petContent) then
            saved.happyLevel = params.petHappy - getDecay(saved.loyalty)
        elseif happinessRank == 1 and saved.happyLevel >= params.petContent then
            saved.happyLevel = params.petContent - getDecay(saved.loyalty)
        end
    else
        if happinessRank == 3 then
            if saved.happyLevel < params.petHappy then
                saved.happyLevel = params.petHappy
            end
        elseif happinessRank == 2 then
            if saved.happyLevel >= params.petHappy then
                saved.happyLevel = params.petHappy - getDecay(saved.loyalty)
            elseif saved.happyLevel < params.petContent then
                saved.happyLevel = params.petContent
            end
        elseif saved.happyLevel >= params.petContent then
            saved.happyLevel = params.petContent - getDecay(saved.loyalty)
        end
        return
    end
    saved.happinessRank = happinessRank
end

local function updatePet()
    local petExists = UnitExists("pet")
    if petExists then
        aura_env.saved.petID = UnitGUID("pet"):sub(-8)
    elseif not aura_env.saved.petID then
        return
    end
    local petID = aura_env.saved.petID
    aura_env.saved.pets[petID] = aura_env.saved.pets[petID] or {}
    saved = aura_env.saved.pets[petID]
    
    saved.loyalty = saved.loyalty or 1
    saved.happinessRank = saved.happinessRank or 1
    saved.happyLevel = saved.happyLevel or 50
    dPrint(saved.happyLevel)
end
updatePet()

local function update(allStates)
    local total = 1000/3
    local happyZone = saved.happyLevel - floor(saved.happyLevel / total)*total
    --[[    if saved.happyLevel >= params.petHappy then
        happyZone = saved.happyLevel - params.petHappy
        total = 1000/3
    elseif saved.happyLevel >= params.petContent then
        happyZone = saved.happyLevel - params.petContent
        total = 1000/3
    else
        happyZone = saved.happyLevel
        total = 1000/3
    end ]]
    local tempDecay = getDecay(saved.loyalty)
    local timeRemaining = happyZone / tempDecay
    
    local show = true
    local changed = true
    allStates[1] = {
        show = show,
        changed = changed,
        progressType = "static",
        value = timeRemaining,
        total = total / tempDecay,
        happiness = saved.happyLevel,
    }
end

local eTime
local prevTime = GetTime()
local function decay()
    saved.happyLevel = saved.happyLevel-getDecay(saved.loyalty)*(eTime-prevTime)
    prevTime = eTime
end

function happiness:trigger(allStates,e)
    if e == "OPTIONS" then return false end
    eTime = GetTime()
    if self.trigger_exp and eTime < self.trigger_exp then
        return false
    end
    self.trigger_exp = eTime + 1
    
    if not UnitExists("pet") then
        return false
    end
    saved.loyalty = getLoyalty()
    if not saved.loyalty then return false end
    decay()
    update(allStates)
    return true
end

function happiness:eventTrigger(allStates,e,...)
    --UNIT_HAPPINESS,UNIT_PET,UNIT_DIED,UNIT_SPELLCAST_SUCCEEDED,PLAYER_ENTERING_WORLD,CLEU:SPELL_PERIODIC_ENERGIZE
    local arg = {...}
    if e == "PLAYER_ENTERING_WORLD" then
        if arg[1] or arg[2] then
            updatePet()
            self.enteredWorld = true
            dPrint(e,saved.happyLevel)
            return
        end
    end
    if not self.enteredWorld then
        return
    end
    if e == "COMBAT_LOG_EVENT_UNFILTERED" then
        local cleu = arg --normal addon: {CombatLogGetCurrentEventInfo()}
        if cleu[2] == "SPELL_PERIODIC_ENERGIZE" and cleu[4] == params.playerGUID and cleu[17] == Enum.PowerType.Happiness and cleu[8]:sub(-8) == aura_env.saved.petID then
            if params.bites[cleu[15]] then
                saved.happyLevel = saved.happyLevel + cleu[15]
                if saved.happyLevel > 1000 then saved.happyLevel = 1000 end
            else
                dPrint("Irregular bite:",cleu[15])
                saved.happyLevel = 1000
                happiness.timestamp = GetTime()
            end
            dPrint(cleu[2],saved.happyLevel)
        end
    else
        if e == "UNIT_HAPPINESS" then
            if arg[1] == "pet" then
                updateHappinessRank()
            end
        elseif e == "UNIT_PET" then
            if arg[1] == "player" then
                if UnitExists("pet") then
                    updatePet()
                    if not self.petExists then
                        prevTime = GetTime()
                        self.petExists = true
                    end
                    dPrint(e,saved.happyLevel)
                else -- Pet gone
                    dPrint(e,"Exists:",UnitExists("pet"),"Existed:",self.petExists,"Is on Taxi:",UnitOnTaxi("player"),"Happyness:",saved.happyLevel)
                    if self.petExists then -- Check if this is the first time we noticed
                        if not UnitOnTaxi("player") then -- Skip if caused by Flight Path
                            saved.happyLevel = saved.happyLevel - 10
                        end
                        self.petExists = false                    
                    end
                    dPrint(e,"Happyness:",saved.happyLevel)
                end
            end
        elseif e == "UNIT_DIED" then
            if arg[1] == "pet" then
                saved.happyLevel = saved.happyLevel - 350
                dPrint(e,saved.happyLevel)
            end
        elseif e == "UNIT_SPELLCAST_SUCCEEDED" then
            if arg[1] == "player" then
                if arg[3] == 2641 then
                    saved.happyLevel = saved.happyLevel - 40
                    dPrint(e,saved.happyLevel)
                end
            end
        end
    end
end

function happiness:display()
    local t = aura_env.state.value
    if not t then return end
    local s = t % 60
    local m = floor(t / 60) % 60
    local h = floor(t / 3600)
    local ret = format("%02d",s)
    ret = (m>0 or h>0) and format("%02d:",m) .. ret or ret
    ret = h>0 and format("%02d:",h) .. ret or ret
    return ret
end