--[[---------------------------------------------------------------------------
    Name: phRaid
    Author: pherl <pherl@live.com>
-----------------------------------------------------------------------------]]

local L = AceLibrary("AceLocale-2.2"):new("phRaid")
local phRBuff = phRaid:NewModule("phRaidBuff",
    "AceEvent-2.0",
    "AceConsole-2.0",
    "AceDebug-2.0"
)
function phRBuff:OnInitialize()
    local _, class = UnitClass("player")
    phRBuff.tooltip = CreateFrame("GameTooltip", "phRaidBuffTooltip", WorldFrame, "GameTooltipTemplate")
    self.tooltip:SetOwner(WorldFrame, "ANCHOR_NONE");
    self.buff = {}
    self.member = {}
    self.textures = {}
    self.coloredDisp = {}
    phRaid.db.defaults.profile.Buffs = {
        {
            name = L["Magic"],
            member = "ALL",
            type = L["Text When Got"],
            disp = L["MagicDisp"],
            color = "3399FF",
            on = class == "PRIEST" or class == "PALADIN",
        },
        {
            name = L["Curse"],
            member = "ALL",
            type = L["Text When Got"],
            disp = L["CurseDisp"],
            color = "9900FF",
            on = class == "MAGE" or class == "DRUID",
        },
        {
            name = L["Poison"],
            member = "ALL",
            type = L["Text When Got"],
            disp = L["PoisonDisp"],
            color = "009900",
            on = class == "DRUID" or class == "PALADIN",
        },
        {
            name = L["Disease"],
            member = "ALL",
            type = L["Text When Got"],
            disp = L["DiseaseDisp"],
            color = "996600",
            on = class == "PRIEST" or class == "PALADIN",
        },    
        {
            name = L["Soulstone Resurrection"],
            member = "ALL",
            type = L["Icon When Got"],
            on = class == "WARLOCK" or class == "PALADIN",
        },
        {
            name = L["Divine Intervention"],
            member = "ALL",
            type = L["Text When Got"],
            disp = L["InterventionDisp"],
            color = "FFFFFF",
            on = class == "PALADIN"
        },
        {
            name = L["Power Word: Fortitude"],
            member = "ALL",
            type = L["Text When Lost"],
            super = L["Prayer of Fortitude"],
            disp = L["FortitudeDisp"],
            color = "FFFFFF",
            on = class == "PRIEST",
        },
        {
            name = L["Power Word: Shield"],
            member = "ALL",
            type = L["Icon When Got"],
            on = class == "PRIEST",
        },
        {
            name = L["Weakened Soul"],
            member = "ALL",
            type = L["Text When Got"],
            disp = L["WeakenedSoulDisp"],
            color = "FF5500",
            on = class == "PRIEST",
        },
        {
            name = L["Renew"],
            member = "ALL",
            type = L["Icon When Got"],
            on = class == "PRIEST",
        },
        {
            name = L["Divine Spirit"],
            member = "ALL",
            type = L["Text When Lost"],
            super = L["Prayer of Spirit"],
            disp = L["SpiritDisp"],
            color = "9900FF",
            on = class == "PRIEST",
        },        
        {
            name = L["Shadow Protection"],
            member = "ALL",
            type = L["Text When Lost"],
            super = L["Prayer of Shadow Protection"],
            disp = L["ShadowProtectionDisp"],
            color = "9900FF",
            on = class == "PRIEST",
        },
        {
            name = L["Power Infusion"],
            member = "All",
            type = L["Icon When Got"],
            disp = L["PowerInfusionDisp"],
            color = "00FF33",
            on = class == "PRIEST",
        },
        {
            name = L["Mark of the Wild"],
            member = "ALL",
            type = L["Text When Lost"],
            super = L["Gift of the Wild"],
            disp = L["MarkOfWildDisp"],
            color = "BC64AA",
            on = class == "DRUID",
        },
        {
            name = L["Innervate"],
            member = "ALL",
            type = L["Text When Got"],
            disp = L["InervateDisp"],
            color = "0000FF",
            on = class == "DRUID",
        },
        {
            name = L["Thorns"],
            member = "ALL",
            type = L["Icon When Got"],
            on = class == "DRUID",
        },
        {
            name = L["Rejuvenation"],
            member = "ALL",
            type = L["Icon When Got"],
            on = class == "DRUID",
        },
        {
            name = L["Regrowth"],
            member = "ALL",
            type = L["Icon When Got"],
            on = class == "DRUID",
        },
        {
            name = L["Abolish Poison"],
            member = "ALL",
            type = L["Icon When Got"],
            on = class == "DRUID",
        },
        {
            name = L["Arcane Intellect"],
            member = "MANA",
            type = L["Text When Lost"],
            super = L["Arcane Brilliance"],
            disp = L["ArcaneIntellectDisp"],
            color = "0000FF",
            on = class == "MAGE",
        },
        {
            name = L["Dampen Magic"],
            member = "ALL",
            type = L["Icon When Got"],
            on = class == "MAGE",
        },
        {
            name = L["Amplify Magic"],
            member = "ALL",
            type = L["Icon When Got"],
            on = class == "MAGE",
        },
        {
            name = L["Blessing of Might"],
            member = "MELEE",
            type = L["Text When Lost"],
            disp = L["BoMightDisp"],
            super = L["Greater Blessing of Might"],
            color = "F48CBA",
            on = class == "PALADIN",
        },
        {
            name = L["Blessing of Wisdom"],
            member = "MANA",
            type = L["Text When Lost"],
            disp = L["BoWisdomDisp"],
            super = L["Greater Blessing of Wisdom"],
            color = "0000FF",
            on = class == "PALADIN",
        },
        {
            name = L["Blessing of Salvation"],
            member = "ALL",
            type = L["Text When Lost"],
            disp = L["BoSalvationDisp"],
            super = L["Greater Blessing of Salvation"],
            color = "F48CBA",
            on = class == "PALADIN",
        },
        {
            name = L["Blessing of Light"],
            member = "ALL",
            type = L["Text When Lost"],
            disp = L["BoLightDisp"],
            super = L["Greater Blessing of Light"],
            color = "FFFFA0",
            on = class == "PALADIN",
        },
        {
            name = L["Blessing of Sanctuary"],
            member = "ALL",
            type = L["Text When Lost"],
            disp = L["BoSanctuaryDisp"], 
            super = L["Greater Blessing of Sanctuary"],
            color = "0000FF",
            on = class == "PALADIN",
        },
        {
            name = L["Blessing of Kings"],
            member = "ALL",
            type = L["Text When Lost"],
            disp = L["BoKingsDisp"],
            super = L["Greater Blessing of Kings"],
            color = "F48CBA",
            on = class == "PALADIN",
        },
        {
            name = L["Blessing of Protection"],
            member = "ALL",
            type = L["Icon When Got"],
            on = class == "PALADIN",
        },
        {
            name = L["Blessing of Sacrifice"],
            member = "ALL",
            type = L["Icon When Got"],
            on = class == "PALADIN",
        },
        {
            name = L["Shield Wall"],
            member = "WARRIOR",
            type = L["Text When Got"],
            disp = L["ShieldWallDisp"],
            color = "FF0000",
            on = class == "PRIEST" or class == "PALADIN" or class == "DRUID" or class == "SHAMAN",
        },
        {
            name = L["Last Stand"],
            member = "WARRIOR",
            type = L["Text When Got"],
            disp = L["LastStandDisp"],
            color = "FF0000",
            on = class == "PRIEST" or class == "PALADIN" or class == "DRUID" or class == "SHAMAN",
        },
        {
            name = L["Gift of Life"],
            member = "WARRIOR",
            type = L["Text When Got"],
            disp = L["GiftOfLifeDisp"],
            color = "FF0000",
            on = class == "PRIEST" or class == "PALADIN" or class == "DRUID" or class == "SHAMAN",
        },
        {
            name = L["Fear Ward"],
            member = "ALL",
            type = L["Icon When Got"],
            on = true,
        },
        {
            name = L["Stealth"],
            member = "ROGUE",
            type = L["Icon When Got"],
            on = true,
        },
        {
            name = L["Vanish"],
            member = "ROGUE",
            type = L["Text When Got"],
            disp = L["VanishDisp"],
            color = "FFFFFF",
            on = true,
        },

    }
--~     phRaid.db.defaults.profile.TextureToName = {
--~         ["Interface\\Icons\\Spell_Shadow_SoulGem"] = L["Soulstone Resurrection"],
--~         ["Interface\\Icons\\Spell_Nature_TimeStop"] = L["Divine Intervention"],
--~         ["Interface\\Icons\\Spell_Holy_WordFortitude"] = L["Power Word: Fortitude"],
--~         ["Interface\\Icons\\Spell_Holy_PrayerOfFortitude"] = L["Prayer of Fortitude"],
--~         ["Interface\\Icons\\Spell_Shadow_AntiShadow"] = L["Shadow Protection"],
--~         ["Interface\\Icons\\Spell_Holy_PrayerofShadowProtection"] = L["Prayer of Shadow Protection"],
--~         ["Interface\\Icons\\Spell_Holy_DivineSpirit"] = L["Divine Spirit"],
--~         ["Interface\\Icons\\Spell_Holy_PrayerofSpirit"] = L["Prayer of Spirit"],
--~         ["Interface\\Icons\\Spell_Holy_Renew"] = L["Renew"],
--~         ["Interface\\Icons\\Spell_Holy_PowerWordShield"] = L["Power Word: Shield"],
--~         ["Interface\\Icons\\Spell_Holy_PowerInfusion"] = L["Power Infusion"],
--~         ["Interface\\Icons\\Spell_Nature_Regeneration"] = L["Mark of the Wild"],
--~         ["Interface\\Icons\\Spell_Nature_Thorns"] = L["Thorns"],
--~         ["Interface\\Icons\\Spell_Nature_Rejuvenation"] = L["Rejuvenation"],
--~         ["Interface\\Icons\\Spell_Nature_ResistNature"] = L["Regrowth"],
--~         ["Interface\\Icons\\Spell_Nature_NullifyPoison_02"] = L["Abolish Poison"],
--~         ["Interface\\Icons\\Spell_Holy_MagicalSentry"] = L["Arcane Intellect"] ,
--~         ["Interface\\Icons\\Spell_Holy_ArcaneIntellect"] = L["Arcane Brilliance"],
--~         ["Interface\\Icons\\Spell_Nature_AbolishMagic"] = L["Dampen Magic"],
--~         ["Interface\\Icons\\Spell_Holy_FlashHeal"] = L["Amplify Magic"],
--~         ["Interface\\Icons\\Spell_Holy_FistOfJustice"] = L["Blessing of Might"],
--~         ["Interface\\Icons\\Spell_Holy_GreaterBlessingofKings"] = L["Greater Blessing of Might"],
--~         ["Interface\\Icons\\Spell_Holy_SealOfWisdom"] = L["Blessing of Wisdom"],
--~         ["Interface\\Icons\\Spell_Holy_GreaterBlessingofWisdom"] = L["Greater Blessing of Wisdom"],
--~         ["Interface\\Icons\\Spell_Holy_SealOfSalvation"] = L["Blessing of Salvation"],
--~         ["Interface\\Icons\\Spell_Holy_GreaterBlessingofSalvation"] = L["Greater Blessing of Salvation"],
--~         ["Interface\\Icons\\Spell_Holy_PrayerOfHealing02"] = L["Blessing of Light"],
--~         ["Interface\\Icons\\Spell_Holy_GreaterBlessingofLight"] = L["Greater Blessing of Light"],
--~         ["Interface\\Icons\\Spell_Nature_LightningShield"] = L["Blessing of Sanctuary"],
--~         ["Interface\\Icons\\Spell_Holy_GreaterBlessingofSanctuary"] = L["Greater Blessing of Sanctuary"],
--~         ["Interface\\Icons\\Spell_Magic_MageArmor"] = L["Blessing of Kings"],
--~         ["Interface\\Icons\\Spell_Magic_GreaterBlessingofKings"] = L["Greater Blessing of Kings"],
--~         ["Interface\\Icons\\Spell_Holy_SealOfProtection"] = L["Blessing of Protection"],
--~         ["Interface\\Icons\\Spell_Holy_SealOfSacrifice"] = L["Blessing of Sacrifice"],
--~     }

--~     phRaid.db.defaults.profile.UntrustTextures = { -- Temporary use, waiting for TBC
--~         ["Interface\\Icons\\Spell_Nature_TimeStop"] = true, -- Sand effect in slss
--~         ["Interface\\Icons\\Spell_Shadow_AntiShadow"] = true, -- Warlock's Shadow Ward
--~         ["Interface\\Icons\\Spell_Nature_LightningShield"] = true, --Lightning Shield
--~     }
    phRaid.options.args.buffswitch = {
        name = L["Buff Fast Switch"],
        type = "group",
        desc = L["Buff Fast Switch"],
        args = {
            enable = {
                name = L["Enable"] .. L["Buff"],
                type = "toggle",
                desc = L["Enable"],
                get = function() return phRaid:IsModuleActive("phRaidBuff") end,
                set = function(value) phRaid:ToggleModuleActive("phRaidBuff", value) end,
                order = 1
            },
            add = {
                name = L["Add"] .. L["Buff"],
                type = "text",
                desc = L["<Full Buff Name>"],
                get = false,
                set = function(value)
                    if not value or value == "" then return end
                    local t = {
                        name = value,
                        member = "ALL",
                        type = L["Icon When Got"],
                        disp = value,
                        on = true,
                        custom = true,
                    }
                    table.insert(phRaid.db.profile.Buffs, t)
                    self:UpdateBuffOptions()
                    self:UpdateBuffTable()
                    self:UNIT_AURA(phRaid.visible)
                end,
                usage = L["<Full Buff Name>"],
                order = 2,
            },
            restoredefault = {
                name = L["Restore Defaults"],
                type = "execute",
                desc = L["This Action Will Clean All Customized Buff Settings"],
                func = function ()
                    phRaid:CopyTable(phRaid.db.defaults.profile.Buffs, phRaid.db.profile.Buffs)
                    phRBuff:UpdateBuffOptions()
                    phRBuff:UpdateBuffTable()
                    phRBuff:UNIT_AURA(phRaid.visible)
                end,
                order = 3,
            },
        },
        order = 25,
    }
    phRaid.options.args.buffsetting = {
        name = L["Buff Settings"],
        type = "group",
        desc = L["Buff Settings"],
        args = {},
        disabled = function() return not phRaid:IsModuleActive("phRaidBuff") end,
        order = 26,
    }
end

function phRBuff:OnEnable()
    self:Debug("phRaidBuff Enabled.")
    phRaid.db.defaults.profile.TextureToName = nil
    self.enabled = true
    self:UpdateBuffOptions()
    self:UpdateBuffTable()
    self:RegisterBucketEvent("UNIT_AURA", 0.2)
    self:RegisterEvent("PHRAID_ROSTER_UPDATE")
    self:PHRAID_ROSTER_UPDATE()
end

function phRBuff:OnDisable()
    self.enabled = false
    for i, f in pairs(phRaid.frames) do
        for j, b in ipairs(f.Buff.frames) do
            b:Hide()
            f.Buff.frames[j] = nil
        end
        f.Buff.num = 0
        self:SetBuffIconsWidth(f.Buff, 0)
        f.Status:SetText("")
    end
end

function phRBuff:UpdateBuffOptions()
    local switchArgs = phRaid.options.args.buffswitch.args
    local setArgs = phRaid.options.args.buffsetting.args
    for i, v in pairs(switchArgs) do if i ~= "enable" and i ~= "add" and i ~= "restoredefault" then switchArgs[i] = nil end end
    for i, v in pairs(setArgs) do setArgs[i] = nil end
    if table.setn then table.setn(switchArgs, 0) end
    phRaid:EraseTable(setArgs)
    local function CreateSwitchSetFunction(index)
        return function(value)
            phRaid.db.profile.Buffs[index].on = value
            phRBuff:UpdateBuffTable()
            phRBuff:UNIT_AURA(phRaid.visible)
        end
    end
    local function CreateGetFunction(index, field)
        return function()
            return phRaid.db.profile.Buffs[index][field]
        end
    end
    local function CreateSetFunction(index, field)
        return function(value)
            phRaid.db.profile.Buffs[index][field] = value
            self:UpdateBuffTable()
            self:UNIT_AURA(phRaid.visible)
        end
    end
    local function CreateMemberSetFunction(index)
        return function(value)
            local funcs = phRaid:ParseStringToFunctions(value)
            if funcs then
                phRaid.db.profile.Buffs[index].member = value
                self.member[index] = funcs
                self:UpdateBuffTable()
                self:UNIT_AURA(phRaid.visible)
            end
        end
    end
    local function CreateTypeSetFunction(i)
        return function(value)
            phRaid.db.profile.Buffs[i].type = value
            self:UpdateBuffTable()
            self:UNIT_AURA(phRaid.visible)
        end
    end
    local function CreateColorGetFunction(index)
        return function()
            local color = phRaid.db.profile.Buffs[index].color
            if not color then return 1, 1, 1 end
            return tonumber(string.sub(color, 1, 2), 16) / 255,
                   tonumber(string.sub(color, 3, 4), 16) / 255,
                   tonumber(string.sub(color, 5, 6), 16) / 255
        end
    end
    local function CreateColorSetFunction(index)
        return function(r, g, b)
            if r > 1 or g > 1 or b > 1 then r, g, b = 1, 1, 1 end
            phRaid.db.profile.Buffs[index].color = string.format("%2X%2X%2X", r * 255, g * 255, b * 255)
            self:UpdateBuffTable()
            self:UNIT_AURA(phRaid.visible)
        end
    end
    local function CreateDisableTextFunction(index)
        return function()
            return phRaid.db.profile.Buffs[index].type == L["Icon When Got"]
        end
    end
    local function CreateSettingDisabledFunction(index)
        return function()
            return not phRaid.db.profile.Buffs[index].on
        end
    end
    local function CreateDeleteFunction(index)
        return function()
            table.remove(phRaid.db.profile.Buffs, index)
            self:UpdateBuffOptions()
            self:UpdateBuffTable()
            self:UNIT_AURA(phRaid.visible)
        end
    end
    local function CreateDeleteDisableFunction(index)
        return not phRaid.db.profile.Buffs[index].custom
    end
    for i, v in ipairs(phRaid.db.profile.Buffs) do
        switchArgs[v.name] = {
            name = v.name,
            type = "toggle",
            desc = v.name,
            get = CreateGetFunction(i, "on"),
            set = CreateSwitchSetFunction(i),
            order = i + 100,
            disabled = function() return not phRaid:IsModuleActive("phRaidBuff") end
        }
        setArgs[v.name] = {
            name = v.name,
            type = "group",
            desc = v.name,
            args = {
                type = {
                    name = L["Buff Show Type"],
                    type = "text",
                    desc = L["Buff Show Type"],
                    get = CreateGetFunction(i, "type"),
                    set = CreateTypeSetFunction(i),
                    validate = {L["Icon When Got"], L["Text When Got"], L["Text When Lost"]},
                    order = 1,
                },
                member = {
                    name = L["Select Member"],
                    type = "text",
                    desc = L["ConditionHelp"],
                    get = CreateGetFunction(i, "member"),
                    set = CreateMemberSetFunction(i),
                    usage = L["ConditionHelp"],
                    order = 2,
                },
                disp = {
                    name = L["Display Buff Name"],
                    type = "text",
                    desc = L["Only Available When 'Type' is Text"],
                    get = CreateGetFunction(i, "disp"),
                    set = CreateSetFunction(i, "disp"),
                    usage = L["Display Buff Name"],
                    order = 3,
                    disabled = CreateDisableTextFunction(i),
                },
                color = {
                    name = L["Display Text Color"],
                    type = "color",
                    desc = L["Only Available When 'Type' is Text"],
                    get = CreateColorGetFunction(i),
                    set = CreateColorSetFunction(i),
                    order = 4,
                    disabled = CreateDisableTextFunction(i),
                    hasAlpha = false,
                },
                delete = {
                    name = L["Delete"],
                    type = "execute",
                    desc = L["Delete"] .. L["Buff"],
                    func = CreateDeleteFunction(i),
                    disabled = CreateDeleteDisableFunction(i),
                }
            },
            order = i,
            disabled = CreateSettingDisabledFunction(i)
        }
    end
end

function phRBuff:UpdateBuffTable()
    phRaid:EraseTable(self.buff)
    phRaid:EraseTable(self.member)
    for i, v in ipairs(phRaid.db.profile.Buffs) do
        if v.on then
            table.insert(self.buff, i)
            self.member[i] = phRaid:ParseStringToFunctions(v.member) or {}
        end
        if v.type ~= L["Icon When Got"] then
            if not v.disp or v.disp == "" then v.disp = v.name end
            if not v.color then v.color = "FFFFFF" end
            self.coloredDisp[i] = "|cFF" .. v.color .. v.disp .. "|r"
        end
    end
end

local cache = {}
local highlight = {
    [L["Magic"]] = "Magic",
    [L["Curse"]] = "Curse",
    [L["Poison"]] = "Poison",
    [L["Disease"]] = "Disease",
}

function phRBuff:UNIT_AURA(units)
    local buff = self.buff
    for unit in pairs(units) do
        phRaid:EraseTable(cache)
        local textures = self.textures
        local f = phRaid.frames[unit]
        local conf = phRaid.db.profile.Buffs
        if f and phRaid.visible[unit] and UnitExists(unit) then
            f.Highlight.shown = nil
            -- For 2.0 duplicated Buffs
            for i = 1, 32 do
                local texture = UnitBuff(unit, i)
                if not texture then break end
                local name = self:GetBuffName(unit, i, texture)
                cache[name] = (cache[name] or 0) + 1
                textures[name] = texture
            end
            for i = 1, MAX_TARGET_DEBUFFS do
                local texture, stack, debuffType = UnitDebuff(unit, i)
                if not texture then break end
                local name
                if debuffType then
                    name = L[debuffType]
                else name = self:GetDebuffName(unit, i, texture) end
                textures[name] = texture
                if stack == 0 then stack = 1 end
                cache[name] = (cache[name] or 0) + stack
            end
            if cache[L["Spirit of Redemption"]] then
                f.impd = true
                phRaid:SetImpDying(f)
            else
                f.impd = false
            end
            local match
            local status = ""
            local count = 1
            for i, v in pairs(buff) do
                if conf[v].type ~= L["Text When Lost"] then
                    match = cache[conf[v].name] or cache[conf[v].super or "nil"]
                else
                    match = not f.unavail and not cache[conf[v].name] and not cache[conf[v].super or "nil"]
                end
                if match then
                    for j, func in pairs(self.member[v]) do
                        if func and func(f.unit, f.class, f.group) then
                            if conf[v].type == L["Icon When Got"] then
                                if f.Buff.num < count then self:CreateBuffFrame(f, count) end
                                local bf = f.Buff.frames[count]
                                bf:SetTexture(textures[conf[v].name])
                                bf:Show()
                                count = count + 1
                            else
                                if type(match) == "number" and match > 1 then 
                                    status = status .. self.coloredDisp[v] .. '(' .. tostring(match) .. ')'
                                else
                                    status = status .. self.coloredDisp[v]
                                end
                                
                            end
                            local dis = highlight[conf[v].name]
                            if dis and not f.Highlight.shown then f.Highlight.shown = dis end
                            break
                        end
                    end
                end
            end
            self:SetBuffIconsWidth(f.Buff, count - 1)
            for i = count, f.Buff.num do
                f.Buff.frames[i]:Hide()
            end
            f.Status:SetText(status)
            if f.Highlight.shown then
                local c = DebuffTypeColor[f.Highlight.shown]
                f.Highlight:SetVertexColor(c.r, c.g, c.b, 1)
                f.Highlight:Show()
            else
                if f.Highlight.mouseover then
                    f.Highlight:SetVertexColor(0, 0, 0)
                    f.Highlight:Show()
                else
                    f.Highlight:Hide()
                end
            end
        end
    end
end

function phRBuff:PHRAID_ROSTER_UPDATE()
    self:UNIT_AURA(phRaid.visible)
end

function phRBuff:GetBuffName(unit, i, texture)
--~     local profile = phRaid.db.profile
--~     if texture and not profile.UntrustTextures[texture] then
--~         local name = profile.TextureToName[texture]
--~         if name then return name end
--~     end
    phRaidBuffTooltip:SetUnitBuff(unit, i)
    return phRaidBuffTooltipTextLeft1:GetText()
--~     local text = phRaidBuffTooltipTextLeft1:GetText()
--~     if not profile.UntrustTextures[texture] then profile.TextureToName[texture] = text end
--~     return text
end

function phRBuff:GetDebuffName(unit, i, texture)
    phRaidBuffTooltip:SetUnitDebuff(unit, i)
    return phRaidBuffTooltipTextLeft1:GetText()
end

--[[---------------------------------------------------------------------------
    Frame Creation
-----------------------------------------------------------------------------]]

function phRBuff:CreateBuffFrame(parent, num)
    local buff
    local opt = phRaid.db.profile.FrameStyle
    for i = parent.Buff.num + 1, num do
        buff = parent:CreateTexture(nil, "OVERLAY")
        buff:SetHeight(opt.BuffSize)
        buff:SetWidth(opt.BuffSize)
        if i == 1 then
            buff:SetPoint("BOTTOMLEFT", parent.Buff, "BOTTOMLEFT", 0)
        else
            buff:SetPoint("BOTTOMLEFT", parent.Buff.frames[i - 1], "BOTTOMRIGHT", 1, 0)
        end
        buff:Hide()
        parent.Buff.frames[i] = buff
        parent.Buff.num = i
    end
end

function phRBuff:SetBuffIconsWidth(buff, num)
    local width = (phRaid.db.profile.FrameStyle.BuffSize + 1) * num
    if num <= 0 then width = 1 end
    buff:SetWidth(width)
end
