-
Notifications
You must be signed in to change notification settings - Fork 1
/
Copy pathCharacters.lua
311 lines (258 loc) · 8.54 KB
/
Characters.lua
1
2
3
4
5
6
7
8
9
10
11
12
13
14
15
16
17
18
19
20
21
22
23
24
25
26
27
28
29
30
31
32
33
34
35
36
37
38
39
40
41
42
43
44
45
46
47
48
49
50
51
52
53
54
55
56
57
58
59
60
61
62
63
64
65
66
67
68
69
70
71
72
73
74
75
76
77
78
79
80
81
82
83
84
85
86
87
88
89
90
91
92
93
94
95
96
97
98
99
100
101
102
103
104
105
106
107
108
109
110
111
112
113
114
115
116
117
118
119
120
121
122
123
124
125
126
127
128
129
130
131
132
133
134
135
136
137
138
139
140
141
142
143
144
145
146
147
148
149
150
151
152
153
154
155
156
157
158
159
160
161
162
163
164
165
166
167
168
169
170
171
172
173
174
175
176
177
178
179
180
181
182
183
184
185
186
187
188
189
190
191
192
193
194
195
196
197
198
199
200
201
202
203
204
205
206
207
208
209
210
211
212
213
214
215
216
217
218
219
220
221
222
223
224
225
226
227
228
229
230
231
232
233
234
235
236
237
238
239
240
241
242
243
244
245
246
247
248
249
250
251
252
253
254
255
256
257
258
259
260
261
262
263
264
265
266
267
268
269
270
271
272
273
274
275
276
277
278
279
280
281
282
283
284
285
286
287
288
289
290
291
292
293
294
295
296
297
298
299
300
301
302
303
304
305
306
307
308
309
310
311
local addonName = ...
local addon = _G[addonName]
local WHITE = "|cFFFFFFFF"
local THIS_ACCOUNT = "Default"
local INFO_REALM_LINE = 0
local INFO_CHARACTER_LINE = 1
local INFO_TOTAL_LINE = 2
local THISREALM_THISACCOUNT = 1
local THISREALM_ALLACCOUNTS = 2
local ALLREALMS_THISACCOUNT = 3
local ALLREALMS_ALLACCOUNTS = 4
addon.Characters = {}
local ns = addon.Characters -- ns = namespace
local characterList
local view
local function ProcessRealms(func)
local mode = addon.Options:Get("TabSummaryMode")
local thisRealm = GetRealmName()
-- this account only
if mode == THISREALM_THISACCOUNT then
func(THIS_ACCOUNT, thisRealm)
elseif mode == ALLREALMS_THISACCOUNT then
for realm in pairs(DataStore:GetRealms()) do
func(THIS_ACCOUNT, realm)
end
-- all accounts
elseif mode == THISREALM_ALLACCOUNTS then
for account in pairs(DataStore:GetAccounts()) do
for realm in pairs(DataStore:GetRealms(account)) do
if realm == thisRealm then
func(account, realm)
end
end
end
elseif mode == ALLREALMS_ALLACCOUNTS then
for account in pairs(DataStore:GetAccounts()) do
for realm in pairs(DataStore:GetRealms(account)) do
func(account, realm)
end
end
end
end
local totalMoney
local totalPlayed
local totalLevels
local realmCount
local function AddRealm(AccountName, RealmName)
local comm = Altoholic.Comm.Sharing
if comm.SharingInProgress then
if comm.account == AccountName and RealmName == GetRealmName() then
-- if we're trying to add the account+realm we're currently copying, then don't add it now.
return
end
end
local realmMoney = 0
local realmPlayed = 0
local realmLevels = 0
local realmBagSlots = 0
local realmFreeBagSlots = 0
local realmBankSlots = 0
local realmFreeBankSlots = 0
local SkillsCache = { {name = "", rank = 0}, {name = "", rank = 0} }
-- 1) Add the realm name
table.insert(characterList, { linetype = INFO_REALM_LINE + (realmCount*3),
isCollapsed = false,
account = AccountName,
realm = RealmName
} )
-- 2) Add the characters
for characterName, character in pairs(DataStore:GetCharacters(RealmName, AccountName)) do
SkillsCache[1].name = ""
SkillsCache[1].rank = 0
SkillsCache[1].spellID = nil
SkillsCache[2].name = ""
SkillsCache[2].rank = 0
SkillsCache[2].spellID = nil
local i = 1
local professions = DataStore:GetPrimaryProfessions(character)
if professions then
for SkillName, s in pairs(professions) do
SkillsCache[i].name = SkillName
SkillsCache[i].rank = DataStore:GetSkillInfo(character, SkillName)
SkillsCache[i].spellID = DataStore:GetProfessionSpellID(SkillName)
i = i + 1
if i > 2 then -- it seems that under certain conditions, the loop continues after 2 professions.., so break
break
end
end
end
table.insert(characterList, { linetype = INFO_CHARACTER_LINE + (realmCount*3),
key = character,
skillName1 = SkillsCache[1].name,
skillRank1 = SkillsCache[1].rank,
spellID1 = SkillsCache[1].spellID,
skillName2 = SkillsCache[2].name,
skillRank2 = SkillsCache[2].rank,
spellID2 = SkillsCache[2].spellID,
cooking = DataStore:GetCookingRank(character),
firstaid = DataStore:GetFirstAidRank(character),
fishing = DataStore:GetFishingRank(character),
riding = DataStore:GetRidingRank(character),
} )
realmLevels = realmLevels + (DataStore:GetCharacterLevel(character) or 0)
realmMoney = realmMoney + (DataStore:GetMoney(character) or 0)
realmPlayed = realmPlayed + (DataStore:GetPlayTime(character) or 0)
realmBagSlots = realmBagSlots + (DataStore:GetNumBagSlots(character) or 0)
realmFreeBagSlots = realmFreeBagSlots + (DataStore:GetNumFreeBagSlots(character) or 0)
realmBankSlots = realmBankSlots + (DataStore:GetNumBankSlots(character) or 0)
realmFreeBankSlots = realmFreeBankSlots + (DataStore:GetNumFreeBankSlots(character) or 0)
end -- end char
-- 3) Add the totals
table.insert(characterList, { linetype = INFO_TOTAL_LINE + (realmCount*3),
level = WHITE .. realmLevels,
money = realmMoney,
played = Altoholic:GetTimeString(realmPlayed),
bagSlots = realmBagSlots,
freeBagSlots = realmFreeBagSlots,
bankSlots = realmBankSlots,
freeBankSlots = realmFreeBankSlots
} )
totalMoney = totalMoney + realmMoney
totalPlayed = totalPlayed + realmPlayed
totalLevels = totalLevels + realmLevels
realmCount = realmCount + 1
end
function ns:BuildList()
characterList = characterList or {}
wipe(characterList)
totalMoney = 0
totalPlayed = 0
totalLevels = 0
realmCount = 0 -- will be required for sorting purposes
ProcessRealms(AddRealm)
AltoholicFrameTotalLv:SetText(format("%s |rLv", WHITE .. totalLevels))
AltoholicFrameTotalGold:SetText(format(GOLD_AMOUNT_TEXTURE, floor( totalMoney / 10000 ), 13, 13))
AltoholicFrameTotalPlayed:SetText(floor(totalPlayed / 86400) .. "|cFFFFD700d")
end
local function AddRealmView(AccountName, RealmName)
for index, line in pairs(characterList) do
if mod(line.linetype, 3) == INFO_REALM_LINE then
if (line.account == AccountName) and (line.realm == RealmName) then
-- insert index to current line (INFO_REALM_LINE)
table.insert(view, index)
index = index + 1
-- insert index to the rest of the realm
local linetype = mod(characterList[index].linetype, 3)
while (linetype ~= INFO_REALM_LINE) do
table.insert(view, index)
index = index + 1
if index > #characterList then
return
end
linetype = mod(characterList[index].linetype, 3)
end
return
end
end
end
end
function ns:BuildView()
-- The character info index is a small table that basically indexes character info
-- ex: character info contains data for 4 realms on two accounts, but the index only cares about the summary tab filter,
-- and indexes just one realm, or one account
view = view or {}
wipe(view)
ProcessRealms(AddRealmView)
end
local function SortByPrimarySkill(a, b, skillName, ascending)
if (a.linetype ~= b.linetype) then -- sort by linetype first ..
return a.linetype < b.linetype
else -- and when they're identical, sort by field xx
if mod(a.linetype, 3) ~= INFO_CHARACTER_LINE then
return false -- don't swap lines if they're not INFO_CHARACTER_LINE
end
local skillA = DataStore:GetSkillInfo(a.key, a[skillName])
local skillB = DataStore:GetSkillInfo(b.key, b[skillName])
if ascending then
return skillA < skillB
else
return skillA > skillB
end
end
end
local function SortByFunction(a, b, func, ascending)
if (a.linetype ~= b.linetype) then -- sort by linetype first ..
return a.linetype < b.linetype
else -- and when they're identical, sort by func xx
if mod(a.linetype, 3) ~= INFO_CHARACTER_LINE then
return false -- don't swap lines if they're not INFO_CHARACTER_LINE
end
local retA = DataStore[func](self, a.key) or 0 -- set to zero if a return value is nil, so that they can be compared
local retB = DataStore[func](self, b.key) or 0
if ascending then
return retA < retB
else
return retA > retB
end
end
end
function ns:Sort(frame, field)
local ascending = frame.ascendingSort
-- Primary Skill
if (field == "skillName1") or (field == "skillName2") then
table.sort(characterList, function(a, b) return SortByPrimarySkill(a, b, field, ascending)
end)
else
table.sort(characterList, function(a, b) return SortByFunction(a, b, field, ascending) end)
end
addon.Tabs.Summary:Refresh()
end
function ns:Get(index)
return characterList[index]
end
function ns:GetView()
return view
end
function ns:GetNum()
return #characterList or 0
end
function ns:GetInfo(index)
-- with the line number in the characterList table, return the name, realm & account of a char.
local lineType = ns:GetLineType(index)
if lineType == INFO_REALM_LINE then
local line = characterList[index]
return _, line.realm, line.account
elseif lineType == INFO_CHARACTER_LINE then
local account, realm, name = strsplit(".", characterList[index].key)
return name, realm, account
end
end
function ns:GetLineType(index)
return mod(characterList[index].linetype, 3)
end
function ns:GetField(index, field)
local character = characterList[index]
if character then
return character[field]
end
end
function ns:ToggleView(frame)
for _, line in pairs(characterList) do
if mod(line.linetype, 3) == INFO_REALM_LINE then
line.isCollapsed = (frame.isCollapsed) or false
end
end
end
function ns:ToggleHeader(frame)
local line = frame:GetParent():GetID()
if line == 0 then return end
local header = characterList[line]
if header.isCollapsed ~= nil then
if header.isCollapsed == true then
header.isCollapsed = false
else
header.isCollapsed = true
end
end
end