--[[ PvPLog Author: Josh Estelle Version: 0.4.6 Last Modified: 2005-04-27 ]] -- version information local VER_NUM = 0; local VER_SUB = 4; local VER_REL = 6; -- Function hooks local lOriginalChatFrame_OnEvent; -- Local variables local variablesLoaded = false; local initialized = false; local realm = ""; local player = ""; local plevel = -1; local NUMRECENT = 10; local recentTargets = { }; local NUMDAMAGED = 5; local damagedTargets = { }; local lastDamagerToMe = ""; local lastDing = -1000; local yourDamageMatch = { -- Your damage or healing -- ENGLISH { pattern = "Your (.+) hits (.+) for (%d+)", spell = 0, mob = 1, pts = 2 }, { pattern = "Your (.+) crits (.+) for (%d+)", spell = 0, mob = 1, pts = 2 }, { pattern = "You drain (%d+) (.+) from (.+)", mob = 2, pts = 0, stat = 1 }, { pattern = "Your (.+) causes (.+) (%d+) damage", spell = 0, mob = 1, pts = 2 }, { pattern = "You reflect (%d+) (.+) damage to (.+)", mob = 2, pts = 0, type = 1 }, { pattern = "(.+) suffers (%d+) (.+) damage from your (.+)", spell = 3, mob = 0, pts = 1, type = 2 }, { pattern = "You hit (.+) for (%d+)", mob = 0, pts = 1 }, { pattern = "You crit (.+) for (%d+)", mob = 0, pts = 1 } -- GERMAN }; local damageToYouMatch = { { pattern = "(.+)'s (.+) hits you for (%d+)", spell = 1, pts = 2, cause = 0 }, { pattern = "(.+)'s (.+) crits you for (%d+)", spell = 1, pts = 2, cause = 0 }, { pattern = "(.+) drains (%d+) (.+) from you", pts = 1, stat = 2, cause = 0 }, { pattern = "(.+)'s (.+) causes you (%d+) damage", spell = 1, pts = 2, cause = 0 }, { pattern = "(.+) reflects (%d+) (.+) damage to you", pts = 1, type = 2, cause = 0 }, { pattern = "You suffer (%d+) (.+) damage from (.+)'s (.+)", spell = 3, pts = 0, type = 1, cause = 2 }, { pattern = "(.+) hits you for (%d+)", pts = 1, cause = 0 }, { pattern = "(.+) crits you for (%d+)", pts = 1, cause = 0 } }; local RED = "|cffff0000"; local GREEN = "|cff00ff00"; local BLUE = "|cff0000ff"; local MAGENTA = "|cffff00ff"; local YELLOW = "|cffffff00"; local CYAN = "|cff00ffff"; local WHITE = "|cffffffff"; -- Called OnLoad of the add on function PvPLogOnLoad() PvPLogChatMsg(CYAN .. "PvPLog Loaded, type " .. RED .. "/pvplog" .. CYAN .. " for useage"); -- respond to saved variable load this:RegisterEvent("VARIABLES_LOADED"); -- respond to player entering the world this:RegisterEvent("PLAYER_ENTERING_WORLD"); -- respond to player name update this:RegisterEvent("UNIT_NAME_UPDATE"); -- respond when player dies this:RegisterEvent("PLAYER_DEAD"); -- respond to when hostiles die this:RegisterEvent("CHAT_MSG_COMBAT_HOSTILE_DEATH"); -- respond when our target changes this:RegisterEvent("PLAYER_TARGET_CHANGED"); -- respond to when you change mouseovers this:RegisterEvent("UPDATE_MOUSEOVER_UNIT"); -- keep track of players level this:RegisterEvent("PLAYER_LEVEL_UP"); end function PvPLogOnEvent() -- loads and initializes our variables if (event == "VARIABLES_LOADED") then variablesLoaded = true; PvPLogInitialize(); -- initialize when entering world elseif( event == "PLAYER_ENTERING_WORLD" ) then PvPLogInitialize(); -- initialize when name changes elseif( event == "UNIT_NAME_UPDATE" ) then PvPLogInitialize(); -- keep track of players level elseif( event == "PLAYER_LEVEL_UP" ) then plevel = UnitLevel("player"); -- respond to player death, tracking if another player killed us elseif( event == "PLAYER_DEAD" ) then -- initialize if we're not for some reason PvPLogInitialize(); if( not initialized ) then return; end -- did we find in target list local found = false; -- make sure we have a last damager -- and are enabled if( lastDamagerToMe == nil or lastDamagerToMe == "" or not PvPLogData[realm][player].enabled) then return; end -- search in player list table.foreach( recentTargets, function(i,v) if( v.name == lastDamagerToMe ) then PvPLogChatMsg(CYAN .. "PvP death logged, killed by: " .. RED .. v.name); PvPLogRecord(v.name, v.level, v.race, v.class, v.guild, true, false); found = true; return 1; end end); -- if killer not found in targets, try to target them so we can check they are a PC if( not found ) then TargetByName(lastDamagerToMe); if( UnitName("target") == lastDamagerToMe and UnitIsPlayer("target") ) then PvPLogChatMsg(CYAN .. "PvP death logged, killed by: " .. RED .. lastDamagerToMe); PvPLogRecord(lastDamagerToMe, UnitLevel("target"), UnitRace("target"), UnitClass("target"), GetGuildInfo("target"), true, false); end end -- add record to mouseover elseif( event == "UPDATE_MOUSEOVER_UNIT" ) then -- initialize if we're not for some reason PvPLogInitialize(); if( not initialized ) then return; end -- adds record to mouseover if it exists if( UnitExists("mouseover") and PvPLogData[realm][player].enabled ) then local total = PvPLogGetPvPTotals(UnitName("mouseover")); local guildTotal = PvPLogGetGuildTotals(GetGuildInfo("mouseover")); -- local tooltipcount = 4; if( total and (total.wins > 0 or total.loss > 0) ) then if( PvPLogData[realm][player].battles[UnitName("mouseover")].enemy ) then GameTooltip:AddLine(CYAN .. "PvP: " .. GREEN .. total.wins .. CYAN .. " / " .. RED .. total.loss, 1.0, 1.0, 1.0, 0 ); else GameTooltip:AddLine(CYAN .. "Duels: " .. GREEN .. total.wins .. CYAN .. " / " .. RED .. total.loss, 1.0, 1.0, 1.0, 0 ); end -- getglobal(GameTooltip:GetName().."TextLeft"..tooltipcount):SetTextColor( 0.05, 1.0, 0.05 ); -- tooltipcount = tooltipcount + 1; GameTooltip:SetHeight( GameTooltip:GetHeight() + GameTooltip:GetHeight() / GameTooltip:NumLines() ); end if( guildTotal and (guildTotal.wins > 0 or guildTotal.loss > 0) and (not total or total.wins ~= guildTotal.wins or total.loss ~= guildTotal.loss) ) then if( not PvPLogFriends(UnitRace("mouseover"), UnitRace("player")) ) then GameTooltip:AddLine(CYAN .. "Guild PvP: " .. GREEN .. guildTotal.wins .. CYAN .. " / " .. RED .. guildTotal.loss, 1.0, 1.0, 1.0, 0 ); else GameTooltip:AddLine(CYAN .. "Guild Duels: " .. GREEN .. guildTotal.wins .. CYAN .. " / " .. RED .. guildTotal.loss, 1.0, 1.0, 1.0, 0 ); end -- getglobal(GameTooltip:GetName().."TextLeft"..tooltipcount):SetTextColor( 0.05, 1.0, 0.05 ); -- tooltipcount = tooltipcount + 1; GameTooltip:SetHeight( GameTooltip:GetHeight() + GameTooltip:GetHeight() / GameTooltip:NumLines() ); end -- if( GetGuildInfo("mouseover") ) then -- GameTooltip:AddLine(WHITE .. GetGuildInfo("mouseover")); -- GameTooltip:SetHeight( GameTooltip:GetHeight() + -- GameTooltip:GetHeight() / GameTooltip:NumLines() ); -- end if( lastDing <= GetTime()-PvPLogData[realm][player].dingTimeout and not UnitInParty("mouseover") and UnitIsPlayer("mouseover") and ((total and (total.wins > 0 or total.loss > 0) and PvPLogData[realm][player].ding ~= "never") or (guildTotal and (guildTotal.wins > 0 or guildTotal.loss > 0) and PvPLogData[realm][player].ding ~= "noguild" and PvPLogData[realm][player].ding ~= "noguildorduel" and PvPLogData[realm][player].ding ~= "never" )) and (UnitIsEnemy("player", "mouseover") or (PvPLogData[realm][player].ding ~= "noduel" and PvPLogData[realm][player].ding ~= "never" and PvPLogData[realm][player].ding ~= "noguildorduel")) ) then if( PvPLogData[realm][player].dispLocation == "chat" ) then local msg = CYAN .. "PvPLog: " .. RED .. UnitName("mouseover") .. CYAN .. " (" .. UnitLevel("mouseover") .. "," .. UnitRace("mouseover") .. "," .. UnitClass("mouseover"); if( GetGuildInfo("mouseover") ) then msg = msg .. ", " .. GetGuildInfo("mouseover"); end msg = msg .. ") -- "; if( total and (total.wins > 0 or total.loss > 0) ) then msg = msg .. GREEN .. total.wins .. CYAN .. " / " .. RED .. total.loss; end if( GetGuildInfo("mouseover") and guildTotal and (guildTotal.wins > 0 or guildTotal.loss > 0) and (not total or total.wins ~= guildTotal.wins or total.loss ~= guildTotal.loss) ) then msg = msg .. CYAN .. " (Guild: " .. GREEN .. guildTotal.wins.. CYAN .. " / " .. RED .. guildTotal.loss.. CYAN .. ")"; end PvPLogChatMsg(msg); else local msg = "PvPLog: " .. UnitName("mouseover") .. " (" .. UnitLevel("mouseover") .. "," .. UnitRace("mouseover") .. "," .. UnitClass("mouseover"); if( GetGuildInfo("mouseover") ) then msg = msg .. ", " .. GetGuildInfo("mouseover"); end msg = msg .. ") -- "; if( total and (total.wins > 0 or total.loss > 0) ) then msg = msg .. total.wins.. " / " .. total.loss; end if( GetGuildInfo("mouseover") and guildTotal and (guildTotal.wins > 0 or guildTotal.loss > 0) and (not total or total.wins ~= guildTotal.wins or total.loss ~= guildTotal.loss) ) then msg = msg .. " (Guild: " .. guildTotal.wins.. " / " .. guildTotal.loss.. ")"; end PvPLogFloatMsg(msg, "cyan"); end PlaySound(PvPLogData[realm][player].dingSound); lastDing = GetTime(); end end -- keep track of those we've targeted elseif (event == "PLAYER_TARGET_CHANGED") then -- initialize if we're not for some reason PvPLogInitialize(); if( not initialized ) then return; end local field = getglobal("PvPLogTargetText"); field:Hide(); field:SetText(""); -- if we're enabled if( PvPLogData[realm][player].enabled ) then PvPLogUpdateTargetText(); -- if we have a vaild target, its a player, and its an enemy if( UnitName("target") and UnitIsPlayer("target") and UnitIsEnemy("player", "target") ) then -- will contain about target local target = { }; target.name = UnitName("target"); target.level = UnitLevel("target"); target.race = UnitRace("target"); target.class = UnitClass("target"); target.guild = GetGuildInfo("target"); -- add to our list of recent targets table.insert( recentTargets, target ); -- remove if we've hit our cap if( table.getn( recentTargets ) > NUMRECENT ) then table.remove( recentTargets, 1 ); end end end -- record a hostile death, if we killed them elseif( event == "CHAT_MSG_COMBAT_HOSTILE_DEATH" ) then -- initialize if we're not for some reason PvPLogInitialize(); if( not initialized ) then return; end -- if we're enabled if( PvPLogData[realm][player].enabled ) then -- get name local index = string.find( arg1, " dies." ); if( not index ) then return; end local value = string.sub( arg1, 0, index-1 ); -- if we have a name if( value ) then -- search in damaged list table.foreach( damagedTargets, function(i,v) if( v.name == value ) then PvPLogChatMsg(CYAN .. "PvP kill logged: " .. GREEN .. v.name); PvPLogRecord(v.name, v.level, v.race, v.class, v.guild, true, true); return 1; end end); end end end end -- Helper Functions function PvPLogSetEnabled(toggle) toggle = string.lower(toggle); if (toggle == "off") then PvPLogData[realm][player].enabled = false; PvPLogFloatMsg(CYAN .. "PvPLog " .. WHITE .. "Off"); else PvPLogData[realm][player].enabled = true; PvPLogFloatMsg(CYAN .. "PvPLog " .. WHITE .. "On"); end end function PvPLogSetDisplayLoc(loc) PvPLogData[realm][player].dispLocation = loc; PvPLogFloatMsg(CYAN .. "PvPLog display location: " .. WHITE .. loc); end function PvPLogSlashHandler(msg) -- initialize if we're not for some reason PvPLogInitialize(); if( not initialized ) then return; end local firsti, lasti, command, value = string.find (msg, "(%w+) \"(.*)\""); if (command == nil) then firsti, lasti, command, value = string.find (msg, "(%w+) (%w+)"); end if (command == nil) then firsti, lasti, command = string.find(msg, "(%w+)"); end --PvPLogChatMsg(msg); --PvPLogChatMsg(command); --PvPLogChatMsg(value); -- respond to commands if (command == nil) then PvPLogDisplayUsage(); elseif (string.lower(command) == "reset") then if( value == "confirm" ) then PvPLogData[realm][player] = { }; PvPLogData[realm][player].battles = { }; PvPLogData[realm][player].enabled = true; PvPLogData[realm][player].dispLocation = "overhead"; PvPLogData[realm][player].ding = "always"; PvPLogData[realm][player].dingSound = "AuctionWindowOpen"; PvPLogData[realm][player].dingTimeout = 120.0; PvPLogData[realm][player].notifyKill = "none"; PvPLogData[realm][player].notifyDeath = "none"; PvPLogData[realm][player].notifyKillText = "I killed $n (Level $l %r %c) at [%x,%y] in %z."; PvPLogData[realm][player].notifyDeathText = "%n (Level %l %r %c) killed me at [%x,%y] in %z."; PvPLogData[realm][player].version = VER_NUM.."."..VER_SUB.."."..VER_REL; PvPLogChatMsg(CYAN .. "PvPLog " .. MAGENTA .. "Reset" .. CYAN .. " Completely!"); end elseif( string.lower(command) == "notifykillstext") then if( value == "long" ) then value = "I killed %n (Level %l %r %c) at [%x,%y] in %z."; elseif( value == "medium" ) then value = "I killed %n (Level %l %r %c) at [%x,%y]."; elseif( value == "short" ) then value = "Killed Level %l %r %c."; elseif( value == "custom" ) then PvPLogChatMsg(CYAN .. "PvPLog: Custom Chat Noftifications\n"); PvPLogChatMsg(CYAN .. " Type the following to use a custom chat notification:\n"); PvPLogChatMsg(CYAN .. " /pvplog notifykillstext \"custom string\" -- or --\n"); PvPLogChatMsg(CYAN .. " /pvplog notifydeathtext \"custom string\"\n"); PvPLogChatMsg(CYAN .. " Where is the text you want used, with\n"); PvPLogChatMsg(CYAN .. " format codes as follows:\n"); PvPLogChatMsg(CYAN .. " %n - name, %l - level, %r - race, %c - class, %g - guild\n"); PvPLogChatMsg(CYAN .. " %x - X:coordinate, %y - Y:coordinate, %z - zone\n"); PvPLogChatMsg(CYAN .. " Example:\n"); PvPLogChatMsg(CYAN .. " /pvplog notifykillstext \"I killed %n (Level %l %r %c) at [%x,%y] in %z.\"\n"); PvPLogChatMsg(CYAN .. " Current setting: " .. PvPLogData[realm][player].notifyKillText .. "\n"); value = nil; else firsti, lasti, value = string.find( msg, "\"(.*)\"" ); end if( value ~= nil ) then PvPLogData[realm][player].notifyKillText = value; PvPLogFloatMsg(CYAN .. "PvPLog Set " .. WHITE .. "notifykillstext" .. CYAN .. " to " .. MAGENTA .. value); end elseif( string.lower(command) == "notifydeathtext") then if( value == "long" ) then value = "%n (Level %l %r %c) killed me at [%x,%y] in %z."; elseif( value == "medium" ) then value = "%n (Level %l %r %c) killed me at [%x,%y]."; elseif( value == "short" ) then value = "Level %l %r %c killed me."; elseif( value == "custom" ) then PvPLogChatMsg(CYAN .. "PvPLog: Custom Chat Noftifications\n"); PvPLogChatMsg(CYAN .. " Type the following to use a custom chat notification:\n"); PvPLogChatMsg(CYAN .. " /pvplog notifykillstext \"custom string\" -- or --\n"); PvPLogChatMsg(CYAN .. " /pvplog notifydeathtext \"custom string\"\n"); PvPLogChatMsg(CYAN .. " Where is the text you want used, with\n"); PvPLogChatMsg(CYAN .. " format codes as follows:\n"); PvPLogChatMsg(CYAN .. " %n - name, %l - level, %r - race, %c - class,\n"); PvPLogChatMsg(CYAN .. " %x - X:coordinate, %y - Y:coordinate, %z - zone\n"); PvPLogChatMsg(CYAN .. " Example:\n"); PvPLogChatMsg(CYAN .. " /pvplog notifydeathtext \"%n (Level %l %r %c) killed me at [%x,%y] in %z.\"\n"); PvPLogChatMsg(CYAN .. " Current setting: " .. PvPLogData[realm][player].notifyDeathText .. "\n"); value = nil else firsti, lasti, value = string.find( msg, "\"(.*)\"" ); end if( value ~= nil ) then PvPLogData[realm][player].notifyDeathText = value; PvPLogFloatMsg(CYAN .. "PvPLog Set " .. WHITE .. "notifydeathtext" .. CYAN .. " to " .. MAGENTA .. value); end elseif( string.lower(command) == "notifykills") then if( value ~= nil ) then PvPLogData[realm][player].notifyKill = value; PvPLogFloatMsg(CYAN .. "PvPLog Set " .. WHITE .. "notifykills" .. CYAN .. " to " .. MAGENTA .. value); else PvPLogDisplayUsage(); end elseif( string.lower(command) == "notifydeath") then if( value ~= nil ) then PvPLogData[realm][player].notifyDeath = value; PvPLogFloatMsg(CYAN .. "PvPLog Set " .. WHITE .. "notifydeath" .. CYAN .. " to " .. MAGENTA .. value); else PvPLogDisplayUsage(); end elseif (string.lower(command) == "targetreset") then PvPLogTargetFrame:ClearAllPoints(); PvPLogTargetFrame:SetPoint("TOP", "TargetFrameHealthBar", "BOTTOM", -2, -5); elseif (string.lower(command) == "enable") then PvPLogSetEnabled("on"); elseif (string.lower(command) == "disable") then PvPLogSetEnabled("off"); elseif (string.lower(command) == "location") then if (value ~= nil) then PvPLogSetDisplayLoc(string.lower(value)); else PvPLogDisplayUsage(); end elseif( string.lower(command) == "version" ) then PvPLogChatMsg(CYAN .. "PvPLog version " .. WHITE .. VER_NUM .. "." .. VER_SUB .. "." .. VER_REL); elseif( string.lower(command) == "dingsound" ) then if( value ~= nil ) then PvPLogData[realm][player].dingSound = value; PvPLogFloatMsg(CYAN .. "PvPLog ding sound: " .. WHITE .. value); else PvPLogDisplayUsage(); end elseif( string.lower(command) == "dingtimeout" ) then if( value ~= nil ) then PvPLogData[realm][player].dingTimeout = value; PvPLogFloatMsg(CYAN .. "PvPLog ding timeout: " .. WHITE .. value); else PvPLogDisplayUsage(); end elseif( string.lower(command) == "ding" ) then if( value ~= nil ) then PvPLogData[realm][player].ding = string.lower(value); PvPLogFloatMsg(CYAN .. "PvPLog ding setting: " .. WHITE .. value); else PvPLogDisplayUsage(); end elseif( string.lower(command) == "stats") then local stats = PvPLogGetStats(); local gankLevel = "Fair Fighter"; if( stats.pvpWinAvgLevelDiff <= -25 ) then gankLevel = "I Have No Mercy"; elseif( stats.pvpWinAvgLevelDiff <= -20 ) then gankLevel = "Newb Masher"; elseif( stats.pvpWinAvgLevelDiff <= -15 ) then gankLevel = "No Seriously, Get a Life"; elseif( stats.pvpWinAvgLevelDiff <= -12 ) then gankLevel = "Get a Life"; elseif( stats.pvpWinAvgLevelDiff <= -9 ) then gankLevel = "Gankity Gank Gank"; elseif( stats.pvpWinAvgLevelDiff <= -6 ) then gankLevel = "Major Ganker"; elseif( stats.pvpWinAvgLevelDiff <= -3 ) then gankLevel = "Minor Ganker"; elseif( stats.pvpWinAvgLevelDiff >= 8 ) then gankLevel = "I Gank GameMasters"; elseif( stats.pvpWinAvgLevelDiff >= 5 ) then gankLevel = "PvP God"; elseif( stats.pvpWinAvgLevelDiff >= 4 ) then gankLevel = "PvP Legend"; elseif( stats.pvpWinAvgLevelDiff >= 3 ) then gankLevel = "Ungankable"; elseif( stats.pvpWinAvgLevelDiff >= 2 ) then gankLevel = "Just try to gank me"; elseif( stats.pvpWinAvgLevelDiff >= 1 ) then gankLevel = "Difficult to Gank"; end PvPLogChatMsg("|cff33ffffPvPLog Statistics:"); PvPLogChatMsg("|cff33ffff Total wins: " .. stats.totalWins .. " (avg.level.diff: " .. (math.floor(stats.totalWinAvgLevelDiff*100)/100) .. ")"); PvPLogChatMsg("|cff33ffff Total losses: " .. stats.totalLoss .. " (avg.level.diff: " .. (math.floor(stats.totalLossAvgLevelDiff*100)/100) .. ")"); PvPLogChatMsg("|cff33ffff PvP wins: " .. stats.pvpWins .. " (avg.level.diff: " .. (math.floor(stats.pvpWinAvgLevelDiff*100)/100) .. ", " .. gankLevel .. ")"); PvPLogChatMsg("|cff33ffff PvP losses: " .. stats.pvpLoss .. " (avg.level.diff: " .. (math.floor(stats.pvpLossAvgLevelDiff*100)/100) .. ")"); PvPLogChatMsg("|cff33ffff Duel wins: " .. stats.duelWins .. " (avg.level.diff: " .. (math.floor(stats.duelWinAvgLevelDiff*100)/100) .. ")"); PvPLogChatMsg("|cff33ffff Duel losses: " .. stats.duelLoss .. " (avg.level.diff: " .. (math.floor(stats.duelLossAvgLevelDiff*100)/100) .. ")"); elseif( string.lower(command) == "find") then PvPLogFind(value); elseif( string.lower(command) == "listall") then PvPLogListAll(); else PvPLogDisplayUsage(); end end function PvPLogDisplayUsage() local text; text = CYAN .. "Usage:\n /PvPLog <"; if( PvPLogData[realm][player].enabled ) then text = text .. WHITE .. "enable" .. CYAN .. " | disable>\n"; else text = text .. "enable | " .. WHITE .. "disable" .. CYAN .. ">\n"; end PvPLogChatMsg(text); PvPLogChatMsg(CYAN .. " /PvPLog reset confirm (DANGER -- erases all records)\n"); PvPLogChatMsg(CYAN .. " /PvPLog listall\n"); text = CYAN .. " /PvPLog location <"; if( PvPLogData[realm][player].dispLocation == "chat" ) then text = text .. WHITE .. "chat" .. CYAN .. " | "; else text = text .. "chat | "; end if( PvPLogData[realm][player].dispLocation == "overhead" ) then text = text .. WHITE .. "overhead" .. CYAN .. " | "; else text = text .. "overhead | "; end if( PvPLogData[realm][player].dispLocation == "none" ) then text = text .. WHITE .. "overhead" .. CYAN .. ">\n"; else text = text .. "none>\n"; end PvPLogChatMsg(text); PvPLogChatMsg(CYAN .. " /PvPLog find \n"); PvPLogChatMsg(CYAN .. " /PvPLog stats\n"); text = CYAN .. " /PvPLog ding <"; if( PvPLogData[realm][player].ding == "always" ) then text = text .. WHITE .. "always" .. CYAN .. " | "; else text = text .. "always | "; end if( PvPLogData[realm][player].ding == "never" ) then text = text .. WHITE .. "never" .. CYAN .. " | "; else text = text .. "never | "; end if( PvPLogData[realm][player].ding == "noguild" ) then text = text .. WHITE .. "noGuild" .. CYAN .. " | "; else text = text .. "noGuild | "; end if( PvPLogData[realm][player].ding == "noduel" ) then text = text .. WHITE .. "noDuel" .. CYAN .. " | "; else text = text .. "noDuel | "; end if( PvPLogData[realm][player].ding == "noguildorduel" ) then text = text .. WHITE .. "noGuildOrDuel" .. CYAN .. ">\n"; else text = text .. "noGuildOrDuel>\n"; end PvPLogChatMsg(text); PvPLogChatMsg(CYAN .. " /PvPLog dingsound (default=AuctionWindowOpen, current=" .. WHITE .. PvPLogData[realm][player].dingSound .. CYAN .. ")\n"); PvPLogChatMsg(CYAN .. " /PvPLog dingtimeout (default=120.0, current=" .. WHITE .. PvPLogData[realm][player].dingTimeout .. CYAN .. ")\n"); local nkills = 0; text = CYAN .. " /PvPLog notifykills <"; if( PvPLogData[realm][player].notifyKill == "none" ) then text = text .. WHITE .. "none" .. CYAN .. " | "; nkills = 1; else text = text .. "none | "; end if( PvPLogData[realm][player].notifyKill == "party" ) then text = text .. WHITE .. "party" .. CYAN .. " | "; nkills = 1; else text = text .. "party | "; end if( PvPLogData[realm][player].notifyKill == "guild" ) then text = text .. WHITE .. "guild" .. CYAN .. " | "; nkills = 1; else text = text .. "guild | "; end if( PvPLogData[realm][player].notifyKill == "raid" ) then text = text .. WHITE .. "raid" .. CYAN .. " | "; nkills = 1; else text = text .. "raid | "; end if( not nkills ) then text = text .. WHITE .. "channelname=" .. PvPLogData[realm][player].notifyKill .. CYAN .. ">\n"; else text = text .. "channelname>\n"; end PvPLogChatMsg(text); nkills = 0; text = CYAN .. " /PvPLog notifydeath <"; if( PvPLogData[realm][player].notifyDeath == "none" ) then text = text .. WHITE .. "none" .. CYAN .. " | "; nkills = 1; else text = text .. "none | "; end if( PvPLogData[realm][player].notifyDeath == "party" ) then text = text .. WHITE .. "party" .. CYAN .. " | "; nkills = 1; else text = text .. "party | "; end if( PvPLogData[realm][player].notifyDeath == "guild" ) then text = text .. WHITE .. "guild" .. CYAN .. " | "; nkills = 1; else text = text .. "guild | "; end if( PvPLogData[realm][player].notifyDeath == "raid" ) then text = text .. WHITE .. "raid" .. CYAN .. " | "; nkills = 1; else text = text .. "raid | "; end if( not nkills ) then text = text .. WHITE .. "channelname=" .. PvPLogData[realm][player].notifyDeath .. CYAN .. ">\n"; else text = text .. "channelname>\n"; end PvPLogChatMsg(text); PvPLogChatMsg(CYAN .. " /PvPLog notifykillstext \n"); PvPLogChatMsg(CYAN .. " /PvPLog notifydeathtext \n"); PvPLogChatMsg(CYAN .. " /PvPLog version\n"); PvPLogChatMsg(CYAN .. " /PvPLog targetreset\n"); end function PvPLogChatMsg(msg) if( DEFAULT_CHAT_FRAME ) then DEFAULT_CHAT_FRAME:AddMessage(msg); end end function PvPLogFloatMsg(msg, color) -- Display overhead message. 7 basic colors available -- Use at most 3 lines here - the rest get lost local r, g, b if (color == nil) then color = "white"; end if (string.lower(color) == "red") then r, g, b = 1.0, 0.0, 0.0; elseif (string.lower(color) == "green") then r, g, b = 0.0, 1.0, 0.0; elseif (string.lower(color) == "blue") then r, g, b = 0.0, 0.0, 1.0; elseif (string.lower(color) == "magenta") then r, g, b = 1.0, 0.0, 1.0; elseif (string.lower(color) == "yellow") then r, g, b = 1.0, 1.0, 0.0; elseif (string.lower(color) == "cyan") then r, g, b = 0.0, 1.0, 1.0; else r, g, b = 1.0, 1.0, 1.0; end UIErrorsFrame:AddMessage(msg, r, g, b, 1.0, UIERRORS_HOLD_TIME); end function PvPLogInitialize() -- get realm and player realm = GetCVar("realmName"); player = UnitName("player"); plevel = UnitLevel("player"); -- check for valid realm and player if( initialized or (not variablesLoaded) or (not realm) or (not plevel) or (not player) or (player == "Unknown Entity") ) then return; end initialized = true; -- Register command handler and new commands SlashCmdList["PvPLogCOMMAND"] = PvPLogSlashHandler; SLASH_PvPLogCOMMAND1 = "/pvplog"; SLASH_PvPLogCOMMAND2 = "/pl"; -- Hook the ChatFrame_OnEvent function lOriginalChatFrame_OnEvent = ChatFrame_OnEvent; ChatFrame_OnEvent = PvPLog_ChatFrame_OnEvent; -- initialize data structure if( PvPLogData == nil ) then PvPLogData = { }; end if( PvPLogData[realm] == nil ) then PvPLogData[realm] = { }; end if( PvPLogData[realm][player] == nil ) then PvPLogData[realm][player] = { }; PvPLogData[realm][player].battles = { }; PvPLogData[realm][player].enabled = true; PvPLogData[realm][player].dispLocation = "overhead"; PvPLogData[realm][player].ding = "always"; PvPLogData[realm][player].dingSound = "AuctionWindowOpen"; PvPLogData[realm][player].dingTimeout = 120.0; PvPLogData[realm][player].notifyKill = "none"; PvPLogData[realm][player].notifyDeath = "none"; PvPLogData[realm][player].notifyKillText = "I killed %n (Level %l %r %c) at [%x,%y] in %z."; PvPLogData[realm][player].notifyDeathText = "%n (Level %l %r %c) killed me at [%x,%y] in %z."; PvPLogData[realm][player].version = VER_NUM.."."..VER_SUB.."."..VER_REL; end if( PvPLogData[realm][player].battles == nil ) then PvPLogData[realm][player].battles = { }; end if( PvPLogData[realm][player].enabled == nil ) then PvPLogData[realm][player].enabled = true; end if( PvPLogData[realm][player].dispLocation == nil ) then PvPLogData[realm][player].dispLocation = "overhead"; end if( PvPLogData[realm][player].dingSound == nil ) then PvPLogData[realm][player].dingSound = "AuctionWindowOpen"; end if( PvPLogData[realm][player].ding == nil ) then PvPLogData[realm][player].ding = "always"; end if( PvPLogData[realm][player].dingTimeout == nil ) then PvPLogData[realm][player].dingTimeout = 120.0; end if( PvPLogData[realm][player].notifyKill == nil ) then PvPLogData[realm][player].notifyKill = "none"; end if( PvPLogData[realm][player].notifyDeath == nil ) then PvPLogData[realm][player].notifyDeath = "none"; end if( PvPLogData[realm][player].notifyKillText == nil ) then PvPLogData[realm][player].notifyKillText = "I killed %n (Level %l %r %c) at [%x,%y] in %z."; end if( PvPLogData[realm][player].notifyDeathText == nil ) then PvPLogData[realm][player].notifyDeathText = "%n (Level %l %r %c) killed me at [%x,%y] in %z."; end if( PvPLogData[realm][player].version == nil ) then PvPLogData[realm][player].version = VER_NUM.."."..VER_SUB.."."..VER_REL; end local stats = PvPLogGetStats(); local allRecords = stats.totalWins + stats.totalLoss; -- Report load PvPLogChatMsg("PvPLog variables loaded: " .. allRecords .. " records (" .. stats.totalWins .. "/" .. stats.totalLoss .. ") for " .. player .. " | " .. realm); end function PvPLogListAll() table.foreach( PvPLogData[realm][player].battles, function( target,v1 ) PvPLogData[realm][player].battles[target].enemy = not PvPLogFriends(UnitRace("player"), v1.race); table.foreach( v1, function( targLevel,v2 ) if( targLevel ~= "race" and targLevel ~= "class" and targLevel ~= "enemy" and targLevel ~= "guild" ) then table.foreach( v2, function( playerLevel, v3 ) local msg = "|cff00ffffPvP: "..target.." ("..targLevel..",".. v1.race ..",".. v1.class; if( v1.guild ) then msg = msg .. "," .. v1.guild; end msg = msg .. ") [".. playerLevel ..",".. v3.wins .."," .. v3.loss .. "]"; PvPLogChatMsg(msg); end); end end) end) end function PvPLog_ChatFrame_OnEvent() lOriginalChatFrame_OnEvent(event, arg1, arg2, arg3, arg4, arg5, arg6, arg7, arg8, arg9); -- initialize if we're not for some reason PvPLogInitialize(); if( not initialized ) then return; end -- occasionally I was getting a nil value on the -- if statement after this one so this is a check -- to make sure that doesn't happen if( not PvPLogData[realm][player] ) then return; end -- check to see if we're enabled if( not PvPLogData[realm][player].enabled ) then return; end if( event and arg1 ) then local s, e; s, e, winner, loser = string.find(arg1, "(.+) has defeated (.+) in a duel"); if( winner ) then --- CHAT_MSG_SYSTEM if( player == winner ) then local v = { }; v.name = loser; TargetByName(loser); if( UnitName("target") == loser ) then v.level = UnitLevel("target"); v.class = UnitClass("target"); v.guild = GetGuildInfo("target"); v.race = UnitRace("target"); else v.level = -1; end PvPLogChatMsg(CYAN .. "PvP duel win logged against: " .. GREEN .. v.name); PvPLogRecord(v.name, v.level, v.race, v.class, v.guild, false, true); elseif( player == loser ) then local v = { }; v.name = winner; TargetByName(winner); if( UnitName("target") == winner ) then v.level = UnitLevel("target"); v.class = UnitClass("target"); v.guild = GetGuildInfo("target"); v.race = UnitRace("target"); else v.level = -1; end PvPLogChatMsg(CYAN .. "PvP duel loss logged against: " .. RED .. v.name); PvPLogRecord(v.name, v.level, v.race, v.class, v.guild, false, false); end end end if( event and (strsub(event, 1, 15) == "CHAT_MSG_COMBAT" or strsub(event, 1, 14) == "CHAT_MSG_SPELL") ) then for index, value in yourDamageMatch do local s, e; local results = { }; s, e, results[0], results[1], results[2], results[3], results[4] = string.find(arg1, value.pattern); if( results[0] ~= nil ) then table.foreach( recentTargets, function(i,v) if( v.name == results[value.mob] ) then table.insert( damagedTargets, v ); if( table.getn( damagedTargets ) > NUMDAMAGED ) then table.remove( damagedTargets, 1 ); end return 1; end end); return; end end for index, value in damageToYouMatch do local s, e; local results = { }; s, e, results[0], results[1], results[2], results[3], results[4] = string.find(arg1, value.pattern); if( results[0] ~= nil ) then lastDamagerToMe = results[value.cause]; return; end end end end function PvPLogFind(search) if( not search ) then return; end search = string.lower(search); table.foreach( PvPLogData[realm][player].battles, function( target,v1 ) local found = string.find( string.lower(target), search ); if( not found) then found = string.find( string.lower(v1.race), search ) end if( not found) then found = string.find( string.lower(v1.class), search ) end if( not found and v1.guild ) then found = string.find( string.lower(v1.guild), search ) end if( found ) then local totals = PvPLogGetPvPTotals(target); local msg = "|cff00ffffPvP: "..target.." (" ..totals.highestLevel .. "," .. v1.race ..",".. v1.class; if( v1.guild ) then msg = msg .. "," .. v1.guild; end msg = msg .. ") Wins: ".. totals.wins ..", Losses:" .. totals.loss .. ", Avg. Level Difference: " .. totals.avgLevelDiff; PvPLogChatMsg(msg); end end) end function PvPLogGetPvPTotals(name) if( not name ) then return nil; end if( not PvPLogData[realm][player].battles[name] ) then return nil; end local total = { }; total.wins = 0; total.loss = 0; total.highestLevel = 0; total.avgLevelDiff = 0; total.winsStr = ""; total.lossStr = ""; total.slashy = true; table.foreach( PvPLogData[realm][player].battles[name], function( targLevel,v2 ) if( targLevel ~= "race" and targLevel ~= "class" and targLevel ~= "enemy" and targLevel ~= "guild" ) then if( targLevel > total.highestLevel ) then total.highestLevel = targLevel; end table.foreach( v2, function( playerLevel, v3 ) total.wins = total.wins + v3.wins; total.loss = total.loss + v3.loss; total.avgLevelDiff = total.avgLevelDiff + (v3.wins+v3.loss)*(targLevel-playerLevel); end); end end); total.avgLevelDiff = total.avgLevelDiff / (total.wins + total.loss); if( total.wins == 1 ) then total.winsStr = "1 win"; elseif( total.wins > 1 ) then total.winsStr = total.wins .. " wins"; else total.slashy = false; end if( total.loss == 1 ) then total.lossStr = "1 loss"; elseif( total.loss > 1 ) then total.lossStr = total.loss .. " losses"; end if( total.slashy and total.loss > 0 ) then total.slashy = " / "; else total.slashy = ""; end return total; end function PvPLogGetGuildTotals(guild) if( not guild ) then return nil; end guild = string.lower(guild); local total = { }; total.wins = 0; total.loss = 0; total.winsStr = ""; total.lossStr = ""; total.slashy = true; table.foreach( PvPLogData[realm][player].battles, function( target,v1 ) if( v1.guild and guild == string.lower(v1.guild) ) then local indiv = PvPLogGetPvPTotals(target); total.wins = total.wins + indiv.wins; total.loss = total.loss + indiv.loss; end end) if( total.wins == 1 ) then total.winsStr = "1 win"; elseif( total.wins > 1 ) then total.winsStr = total.wins .. " wins"; else total.slashy = false; end if( total.loss == 1 ) then total.lossStr = "1 loss"; elseif( total.loss > 1 ) then total.lossStr = total.loss .. " losses"; end if( total.slashy and total.loss > 0 ) then total.slashy = " / "; else total.slashy = ""; end return total; end function PvPLogGetStats() local stats = { }; stats.totalWins = 0; stats.totalWinAvgLevelDiff = 0; stats.totalLoss = 0; stats.totalLossAvgLevelDiff = 0; stats.pvpWins = 0; stats.pvpWinAvgLevelDiff = 0; stats.pvpLoss = 0; stats.pvpLossAvgLevelDiff = 0; stats.duelWins = 0; stats.duelWinAvgLevelDiff = 0; stats.duelLoss = 0; stats.duelLossAvgLevelDiff = 0; stats.levels = { }; stats.levels[0] = { }; stats.levels[1] = { }; stats.levels[2] = { }; stats.levels[3] = { }; stats.levels[4] = { }; stats.levels[5] = { }; stats.levels[6] = { }; stats.levels[7] = { }; stats.levels[8] = { }; stats.levels[9] = { }; stats.levels[10] = { }; stats.levels[0].wins = 0; stats.levels[1].wins = 0; stats.levels[2].wins = 0; stats.levels[3].wins = 0; stats.levels[4].wins = 0; stats.levels[5].wins = 0; stats.levels[6].wins = 0; stats.levels[7].wins = 0; stats.levels[8].wins = 0; stats.levels[9].wins = 0; stats.levels[10].wins = 0; stats.levels[0].loss = 0; stats.levels[1].loss = 0; stats.levels[2].loss = 0; stats.levels[3].loss = 0; stats.levels[4].loss = 0; stats.levels[5].loss = 0; stats.levels[6].loss = 0; stats.levels[7].loss = 0; stats.levels[8].loss = 0; stats.levels[9].loss = 0; stats.levels[10].loss = 0; stats.classes = { }; stats.punchingbag = ""; stats.punchingbagkills = 0; stats.feared = ""; stats.feareddeaths = 0; table.foreach( PvPLogData[realm][player].battles, function( target,v1 ) if( v1.enemy == nil ) then PvPLogData[realm][player].battles[target].enemy = not PvPLogFriends( UnitRace("player"), v1.race ); end table.foreach( v1, function( targLevel,v2 ) if( targLevel ~= "race" and targLevel ~= "class" and targLevel ~= "enemy" and targLevel ~= "guild" ) then table.foreach( v2, function( playerLevel, v3 ) stats.totalWins = stats.totalWins + v3.wins; if( targLevel < 0 ) then stats.totalWinAvgLevelDiff = stats.totalWinAvgLevelDiff + v3.wins*(-targLevel-playerLevel); else stats.totalWinAvgLevelDiff = stats.totalWinAvgLevelDiff + v3.wins*(targLevel-playerLevel); end stats.totalLoss = stats.totalLoss + v3.loss; if( targLevel < 0 ) then stats.totalLossAvgLevelDiff = stats.totalLossAvgLevelDiff + v3.loss*(-targLevel-playerLevel); else stats.totalLossAvgLevelDiff = stats.totalLossAvgLevelDiff + v3.loss*(targLevel-playerLevel); end if( v1.enemy ) then stats.pvpWins = stats.pvpWins + v3.wins; if( targLevel < 0 ) then stats.pvpWinAvgLevelDiff = stats.pvpWinAvgLevelDiff + v3.wins*(targLevel-playerLevel); else stats.pvpWinAvgLevelDiff = stats.pvpWinAvgLevelDiff + v3.wins*(targLevel-playerLevel); end stats.pvpLoss = stats.pvpLoss + v3.loss; if( targLevel < 0 ) then stats.pvpLossAvgLevelDiff = stats.pvpLossAvgLevelDiff + v3.loss*(targLevel-playerLevel); else stats.pvpLossAvgLevelDiff = stats.pvpLossAvgLevelDiff + v3.loss*(targLevel-playerLevel); end else stats.duelWins = stats.duelWins + v3.wins; if( targLevel < 0 ) then stats.duelWinAvgLevelDiff = stats.duelWinAvgLevelDiff + v3.wins*(targLevel-playerLevel); else stats.duelWinAvgLevelDiff = stats.duelWinAvgLevelDiff + v3.wins*(targLevel-playerLevel); end stats.duelLoss = stats.duelLoss + v3.loss; if( targLevel < 0 ) then stats.duelLossAvgLevelDiff = stats.duelLossAvgLevelDiff + v3.loss*(targLevel-playerLevel); else stats.duelLossAvgLevelDiff = stats.duelLossAvgLevelDiff + v3.loss*(targLevel-playerLevel); end end end); end end); end); stats.totalWinAvgLevelDiff = stats.totalWinAvgLevelDiff / stats.totalWins; stats.totalLossAvgLevelDiff = stats.totalLossAvgLevelDiff / stats.totalLoss; stats.pvpWinAvgLevelDiff = stats.pvpWinAvgLevelDiff / stats.pvpWins; stats.pvpLossAvgLevelDiff = stats.pvpLossAvgLevelDiff / stats.pvpLoss; stats.duelWinAvgLevelDiff = stats.duelWinAvgLevelDiff / stats.duelWins; stats.duelLossAvgLevelDiff = stats.duelLossAvgLevelDiff / stats.duelLoss; return stats; end function PvPLogFriends(race1, race2) local alliance = { "Human", "Night Elf", "Dwarf", "Gnome" }; local horde = { "Orc", "Tauren", "Undead", "Troll" }; local found1 = false; local found2 = false; table.foreach( alliance, function( i,v ) if( v == race1 ) then found1 = true; end if( v == race2 ) then found2 = true; end end); if( found1 and found2 ) then return true; end found1 = false; found2 = false; table.foreach( horde, function( i,v ) if( v == race1 ) then found1 = true; end if( v == race2 ) then found2 = true; end end); return (found1 and found2); end function PvPLogRecord(vname,vlevel,vrace,vclass,vguild,venemy,win) -- deal with vlevel being negative 1 when they're 10 levels -- or more greater if( vlevel == -1 ) then vlevel = -plevel - 11; end -- check to see if we've encountered this person before if( PvPLogData[realm][player].battles[vname] == nil ) then PvPLogData[realm][player].battles[vname] = { }; end if( PvPLogData[realm][player].battles[vname][vlevel] == nil ) then PvPLogData[realm][player].battles[vname][vlevel] = { }; end if( PvPLogData[realm][player].battles[vname][vlevel][plevel] == nil ) then PvPLogData[realm][player].battles[vname][vlevel][plevel] = { }; PvPLogData[realm][player].battles[vname][vlevel][plevel].wins = 0; PvPLogData[realm][player].battles[vname][vlevel][plevel].loss = 0; end -- record info PvPLogData[realm][player].battles[vname].race = vrace; PvPLogData[realm][player].battles[vname].class = vclass; PvPLogData[realm][player].battles[vname].guild = vguild; PvPLogData[realm][player].battles[vname].enemy = venemy; local x, y = GetPlayerMapPosition("player"); x = math.floor(x*100); y = math.floor(y*100); local notifyMsg = ""; local notifySystem = nil; local vleveltext = vlevel; if( vlevel < 0 ) then vleveltext = (-vlevel) .. "+"; end if( win ) then PvPLogData[realm][player].battles[vname][vlevel][plevel].wins = PvPLogData[realm][player].battles[vname][vlevel][plevel].wins + 1; notifyMsg = PvPLogData[realm][player].notifyKillText; notifyMsg = string.gsub( notifyMsg, "%%n", vname ); notifyMsg = string.gsub( notifyMsg, "%%l", vleveltext ); notifyMsg = string.gsub( notifyMsg, "%%r", vrace ); notifyMsg = string.gsub( notifyMsg, "%%c", vclass ); if( vguild ) then notifyMsg = string.gsub( notifyMsg, "%%g", vguild ); end notifyMsg = string.gsub( notifyMsg, "%%x", x ); notifyMsg = string.gsub( notifyMsg, "%%y", y ); notifyMsg = string.gsub( notifyMsg, "%%z", GetZoneText() ); --notifyMsg = notifyMsg .. "I killed " .. vname .. -- " (Level " .. vleveltext .. " " .. vrace .. " " .. vclass; --if( vguild ) then -- notifyMsg = notifyMsg .. ", from " .. vguild; --end --notifyMsg = notifyMsg .. ") at [" ..x..","..y .. "] in " .. GetZoneText(); --notifyMsg = notifyMsg .. ") at [" ..x..","..y .. "]"; notifySystem = PvPLogData[realm][player].notifyKill; else PvPLogData[realm][player].battles[vname][vlevel][plevel].loss = PvPLogData[realm][player].battles[vname][vlevel][plevel].loss + 1; --notifyMsg = notifyMsg .. vname .. -- " (Level " .. vleveltext .. " " .. vrace .. " " .. vclass; --if( vguild ) then -- notifyMsg = notifyMsg .. ", from " .. vguild; --end --notifyMsg = notifyMsg .. ") just killed me at [" ..x..","..y .. "]"; notifyMsg = PvPLogData[realm][player].notifyDeathText; notifyMsg = string.gsub( notifyMsg, "%%n", vname ); notifyMsg = string.gsub( notifyMsg, "%%l", vleveltext ); notifyMsg = string.gsub( notifyMsg, "%%r", vrace ); notifyMsg = string.gsub( notifyMsg, "%%c", vclass ); if( vguild ) then notifyMsg = string.gsub( notifyMsg, "%%g", vguild ); end notifyMsg = string.gsub( notifyMsg, "%%x", x ); notifyMsg = string.gsub( notifyMsg, "%%y", y ); notifyMsg = string.gsub( notifyMsg, "%%z", GetZoneText() ); notifySystem = PvPLogData[realm][player].notifyDeath; -- fix to double recording of deaths -- likely caused by blizzard sending PLAYER_DEAD twice lastDamagerToMe = ""; end if( venemy and ((notifySystem == "party" and GetNumPartyMembers() > 0) or (notifySystem == "guild" and GetGuildInfo("player") ) or (notifySystem == "raid" and GetNumRaidMembers() > 0)) ) then SendChatMessage(notifyMsg, notifySystem); elseif( venemy and notifySystem ~= "none" and notifySystem ~= "party" and notifySystem ~= "guild" and notifySystem ~= "raid" ) then PvPLogSendMessageOnChannel(notifyMsg, notifySystem); end PvPLogUpdateTargetText(); end function PvPLogUpdateTargetText() local field = getglobal("PvPLogTargetText"); if( UnitName("target") ) then local total = PvPLogGetPvPTotals(UnitName("target")); local guildTotal = PvPLogGetGuildTotals(GetGuildInfo("target")); local msg = ""; local show = false; if( total and (total.wins > 0 or total.loss > 0) ) then msg = msg .. CYAN .. "PvP: " .. GREEN .. total.wins.. CYAN .. " / " .. RED .. total.loss; show = true; end if( guildTotal and (guildTotal.wins > 0 or guildTotal.loss > 0) and (not total or total.wins ~= guildTotal.wins or total.loss ~= guildTotal.loss) ) then if( show ) then msg = msg .. CYAN .. " - "; end msg = msg .. CYAN .. "Guild: "; msg = msg .. GREEN .. guildTotal.wins.. CYAN .. " / ".. RED .. guildTotal.loss; show = true; end if( show ) then field:SetText(msg); field:Show(); end end end function PvPLogSendMessageOnChannel(message, channelName) local channelNum = PvPLogGetChannelNumber(channelName); if (not channelNum or channelNum == 0) then PvPLogJoinChannel(channelName); channelNum = PvPLogGetChannelNumber(channelName); end if (not channelNum or channelNum == 0) then PvPLogChatMsg(MAGENTA.."PvPLog Error: Not in notification channel \""..channelName.."\"."); return; end SendChatMessage(message, "CHANNEL", GetLanguageByIndex(0), channelNum); end function PvPLogGetChannelNumber(channel) local num = 0; for i = 1, 200, 1 do local channelNum, channelName = GetChannelName(i); if ((channelNum > 0) and channelName and (string.lower(channelName) == string.lower(channel))) then num = channelNum; break; end end return num; end function PvPLogJoinChannel(channelName) local channelNumber = PvPLogGetChannelNumber(channelName); local needToJoin = (channelNumber <= 0); if( needToJoin ) then local i = 1; while ( DEFAULT_CHAT_FRAME.channelList[i] ) do local zoneValue = "nil"; if (DEFAULT_CHAT_FRAME.zoneChannelList[i]) then zoneValue = DEFAULT_CHAT_FRAME.zoneChannelList[i]; end if ( string.lower(DEFAULT_CHAT_FRAME.channelList[i]) == string.lower(channelName) and DEFAULT_CHAT_FRAME.zoneChannelList[i] and DEFAULT_CHAT_FRAME.zoneChannelList[i] > 0) then needToJoin = false; break; end i = i + 1; end JoinChannelByName(channelName, "", DEFAULT_CHAT_FRAME:GetID()); DEFAULT_CHAT_FRAME.channelList[i] = channelName; DEFAULT_CHAT_FRAME.zoneChannelList[i] = 0; end end