Looked at the code, and found two points that might be a start to identifying why it happens.
1. SGT alters the scroll list in a very evil and inefficient way.
Hooking ZO_ScrollList_UpdateScroll and other generic functions is not nice. All hooks referecing SGT_Roster.ColumnUpdateHandler should be removed and replaced with just this one:
Lua Code:
local orgSetupGuildMember = GUILD_ROSTER_MANAGER.SetupGuildMember
function GUILD_ROSTER_MANAGER:SetupGuildMember(control, data)
orgSetupGuildMember(self, control, data)
SGT_Roster.NewColumnAddRow(control, data)
-- it currently doesn't use the second arg, but could, for convenience
end
It could be further optimized by moving sub-control creation to row-control creation callback, but that'd be more work for a negligible effect, so not really that necessary.
2. SGT_Roster.NewColumnAddRow could use a little optimization.
In my opinion it shouldn't construct tooltip strings at all. Their construction should be deferred to the moment right before tooltip display, i.e. OnMouseEnter.
Btw, I'm just guessing, but perhaps the tooltip creation is what eats the memory. There's a loop over MemberChars, with character names being appended to the tooltip one by one, each after the first doing 2 string concats.
ShissuGT.Lib.GetCharInfoIcon does 0 to 3 concats. It should be changed to string.format("|t28:28:%s|t%s", icon, text) -- that will remove the 2 intermediate string allocations.
SGT_Roster.NewCharName consequently does 1 to 7 concats. With fixed GetCharInfoIcon it will be 1 to 3.
So for 8 characters, there will be (1 to 7) + 7 * (3 to 9) concatenations. Due to all the above points combined, this happens every time you scroll the list for all people you currently see (roughly 20). That's 400-1200 string concats. I don't know when Lua discards unused strings, I hope it does at some point, but this looks like it's allocating too many too fast.
Refactored tooltip construction
Lua Code:
local function buildTooltip(MemberChars)
local lines = {}
for charName, charInfo in pairs(MemberChars) do
lines[#lines + 1] = SGT_Roster.NewCharName(charName, charInfo)
end
table.sort(lines) -- making the order consistent can't hurt ;)
return table.concat(lines, "\n")
end
charNameControl.tooltip = nil
charNameControl:SetHandler("OnMouseEnter", function (self)
if self.tooltip == nil then
local MemberChars = SGT_Roster.MemberChars[displayName]
if MemberChars then
self.tooltip = buildTooltip(MemberChars)
else
self.tooltip = false
end
end
if self.tooltip then
ZO_Tooltips_ShowTextTooltip(self, TOP, self.tooltip)
end
end)
charNameControl:SetHandler("OnMouseEnter", function (self)
ZO_Tooltips_HideTextTooltip()
end)