I'm writing an addon to help fill gaps in log parsing websites for the heroic lich king encounter. Right now it's aimed at tracking units grabbed by Val'kyr Shadowguards as well as effective damage done to them (damage above 50% health).
While I've got something that should be functional I have a few problems:
The data it prints is a massive block of text, and more importantly since it's printed locally it can't be logged to chatlog.txt. This means there's no permanent record of it and it tends to be pushed off the chat log quite quickly during the encounter.
Due to the character limit on SendChatMessage, it's not something that will translate cleanly from a print(). My string manipulation abilities are a bit weak and I can't think of any way to cleanly break this down into a compatible size. I'm placing all of the data in a table and forming my large string with table.concat.
Any suggestions for getting the string down to usable sizes and reporting it in individual chat lines without truncating it in the middle of a player's damage or name?
The other problem is an issue of readability and elegance. I'm using a hash table to collect data about effective damage done. The key is the player's name and the value is the damage. I want returned value to be sorted from highest to lowest damage - due to the unpredictably ordered returns when iterating a hash table I had to pass my data to a temporary array to sort it.
While I don't think I can avoid using an array in some form, is it possible to change my data structures to get rid of the temporary table without making the code worse? Or is it possible to do what I'm doing currently better? The relevant code for this particular issue is highlighted.
I actually wrote the same addon for my guild. Though I don't understand your first question completely (why not just print one person, one damage value per line?), I do have something that worked for me for the second problem, so long as you are okay with destroying the data after it is printed (as I do at the end of each pull). This is built on my own framework, but should still be straightforward. Basically, keep finding the max, print it, and discard it. I do top 5 each pull.
if (next(damageBoard)) then
local type = "minor"; -- this type prints to raid
local count = 5;
core:Message("Val'kyr Overkill:", type);
for i=1,count do
local max = 0;
for p,dmg in pairs(damageBoard) do
if (dmg > (damageBoard[max] or 0)) then
max = p;
if (damageBoard[max]) then
core:Message(format("%d. %s - %.1fk", i, max, damageBoard[max]/1000), type);
damageBoard[max] = nil;
I actually wrote the same addon for my guild. Though I don't understand your first question completely (why not just print one person, one damage value per line?)
Some of my code comments are a bit inaccurate in the above - I'm now actually tracking effective damage rather than wasted damage. This data is more appropriate for our specific need but it also means that I need to print all of the users damage to get usable results.
I want to be able to log the chat data via /chatlog (meaning I need to print it to a chat channel) so doing each line individually would result in the user having their chat automatically throttled.
I do have something that worked for me for the second problem, so long as you are okay with destroying the data after it is printed (as I do at the end of each pull). This is built on my own framework, but should still be straightforward. Basically, keep finding the max, print it, and discard it. I do top 5 each pull.
I'm already disposing of my data after each wave is complete (all players dropped) so that's not really a problem. This is an interesting alternative, thanks for the input.