-- The MIT License (MIT) http://opensource.org/licenses/MIT -- Copyright (c) 2014-2016 His Dad -- Some code from the luatz project (MIT Licence) -- Configuration ========== --local dateformat = "%Y-%m-%d, %H:%M" dateformat_log = "%Y-%m-%d, %H:%M:%S" FG_Colour_Not_Complete = "#FFB67D" FG_Colour_Complete = "#000000" BG_Colour_Not_Complete = "#FFB67D" BG_Colour_Complete = "#A4FF5A" Colour_Heading_Complete = "#58FA58" local dname, key, count, ccount, colour, bgcolour --force_lang = "de" -- or "de" or "fr" for debugging -- ======================== version= "56-Beta-01" require( "iuplua" ) require( "iupluacontrols" ) --require( "iupluamatrixex" ) iup.SetGlobal("UTF8MODE","YES") dofile "../../SavedVariables/History.lua" Trials_Dat={} Trials_Order={"N","V","VH"} Grp_Dat={} Grp_Order={"1N","1V","1VH","2N","2V","2VH"} Grp1_Order={"1N","1V","1VH"} Grp2_Order={"2N","2V","2VH"} for _,i in ipairs(Grp_Order) do Grp_Dat[i]={} end for _,i in ipairs(Trials_Order) do Trials_Dat[i]={} end dofile "./data/Keys.lua" --Linking tables, must do first dofile "./data/DLC.lua" --Achievement to Grid lookup, language independent dofile "./data/Group1.lua" -- Grp Mode 1 data, N, V, VH dofile "./data/Group2.lua" -- Grp Mode 2 data, N, V, VH dofile "./data/Public.lua" dofile "./data/Quest2.lua" dofile "./data/Veteran.lua" -- Auxiliary Achievements for Vet Dungeons dofile "./data/WB2.lua" dofile "./data/Trials.lua" dofile "./data/Special.lua" -- Record of non standard Achievement ID's we need to keep. dofile "./data/utility.lua" -- utility functions dofile "./data/Strings.lua" -- String Handling --generate_id () -- Generate the file the addon uses to filter Achievement ID's -- This is used by the in game part history.lua to only record achievements that are used. -- Uncomment when need to run. -- generate achievement lookups from key (cell) for _,i in ipairs(Grp_Order) do Grp_Dat[i].reverse_id = reverse_id(Grp_Dat[i].id) end for _,i in ipairs(Trials_Order) do Trials_Dat[i].reverse_id = reverse_id(Trials_Dat[i].id) end Pub_Dat_Char.reverse_id = reverse_id(Pub_Dat_Char.id) DLC_Dat.reverse_id = reverse_id(DLC_Dat.id) lingua= {} -- Translated data load_lang = function (lang) if lingua[lang] ~= nil then return end local path = "./data/" .. lang .. "/" dofile (path .. lang .. ".lua") dofile (path .. lang .."-data.lua") --Achievement Data from game lingua[lang] = {} lingua[lang].Area_names = Area_names -- dofile writes to global variables lingua[lang].L = L lingua[lang].pub_names = pub_names lingua[lang].grp_names = grp_names lingua[lang].DLC_Location_names = DLC_Location_names lingua[lang].Ach_Detail = Ach_Detail end accounts = {} accounts_list = {} -- String list for selection dialog playerNames = {} -- Get name from ID. for acc,_ in pairs(History_SV["Default"]) do accounts[acc] = {} accounts[acc].worlds = {} accounts[acc].hasblankworlds = false accounts[acc].player = {} accounts[acc].playerIDs = {} -- intermediate table for sorting. WIP. Controls presentation order accounts[acc].playerIDs_vet= {} -- subset of names which are >L50 table.insert(accounts_list, acc) -- === Load Language Tables accounts[acc].lang = (History_SV["Default"][acc]["$AccountWide"].lang) if accounts[acc].lang == nil then accounts[acc].lang = "en" end if force_lang ~= nil then accounts[acc].lang = force_lang -- Force the language for testing end load_lang(accounts[acc].lang) -- Reset Globals Area_names = lingua[accounts[acc].lang].Area_names L = lingua[accounts[acc].lang].L pub_names = lingua[accounts[acc].lang].pub_names grp_names = lingua[accounts[acc].lang].grp_names DLC_Location_names = lingua[accounts[acc].lang].DLC_Location_names Ach_Detail = lingua[accounts[acc].lang].Ach_Detail -- load worlds nworlds = 0 if History_SV["Default"][acc]["$AccountWide"]["worlds"] ~= nil then for i,j in pairs(History_SV["Default"][acc]["$AccountWide"]["worlds"]) do nworlds = nworlds +1 table.insert(accounts[acc].worlds, i) end end -- insert marker for older chars -- table.insert(accounts[acc].worlds, "##NEITHER##") -- Load Character Data for playerID, _ in pairs(History_SV["Default"][acc]["$AccountWide"]["data"]) do if playerID == "" then print("acct: " .. acc) end table.insert (accounts[acc].playerIDs, playerID) accounts[acc].player[playerID] = {} -- stub table to hold char data, later becomes "me" -- local me = accounts[acc].player[playerID] -- shorter reference: our code local thischar = History_SV["Default"][acc]["$AccountWide"]["data"][playerID] -- shorter reference: History DB -- Pull in some char data for processing if thischar.name == nil then -- Old Format -- print("Old Format " .. playerID) me.name = playerID else me.name = thischar.name end playerNames[playerID]=me.name -- == Gender if thischar.Gender =="M" then me.gender = L.Male elseif thischar.Gender == "F" then me.gender = L.Female end -- ==Level local level = thischar.level me.level = level if (level <=50) then me.levelstr = tostring(level) me.isvet = false else me.levelstr = "V" .. tostring(level -50) me.isvet = true table.insert(accounts[acc].playerIDs_vet,playerID) end -- == Cumulative TimePlayed if thischar.timeplayed == nil then me.timeplayed = math.floor(thischar.levels[level].time/60) -- Old version compat else me.timeplayed = math.floor(thischar.timeplayed/60) end -- world if thischar.world == nil then accounts[acc].hasblankworlds = true -- causes display of "##NEITHER## else me.world = thischar.world -- server end -- a quick link to my Achievements me.ach = thischar.ach end table.sort(accounts[acc].playerIDs,function(a,b) return (playerNames[a] < playerNames[b]) end) table.sort(accounts[acc].playerIDs_vet,function(a,b) return (playerNames[a] < playerNames[b]) end) end --[[ ========================================== Iterate over all accounts and PlayerIDs creating display items --]] for acc,_ in pairs (accounts) do -- ==== Accountwide Data -- Setup Log data accounts[acc].logtabs =iup.tabs{} -- Log Display table presentation accounts[acc].logtable = {} accounts[acc].logtable=iup.matrix{numcol=2, numcol_visible=2, numlin=0,numlin_visible=8} accounts[acc].logtable:setcell(0,0, L.TStamp) iup.SetAttribute(accounts[acc].logtable, "ALIGNMENT0", "ACENTER") iup.SetAttribute(accounts[acc].logtable, "ALIGNMENT2", "ALEFT") iup.SetAttribute(accounts[acc].logtable, "WIDTH0", 80) iup.SetAttribute(accounts[acc].logtable, "WIDTH1", 100) iup.SetAttribute(accounts[acc].logtable, "WIDTH2", 300) iup.SetAttribute(accounts[acc].logtable, "READONLY", "YES") -- Load log data local Line=0 local TimeStr = "" accounts[acc].logtable.numlin = Line for _,j in ipairs (History_SV["Default"][acc]["$AccountWide"]["log"]) do Line= Line +1 accounts[acc].logtable.numlin = Line TimeStr = os.date(dateformat_log,j["TimeStamp"]) accounts[acc].logtable:setcell( Line,0, TimeStr) if j["Char"] ~= nil then accounts[acc].logtable:setcell( Line,1, j["Char"]) end accounts[acc].logtable:setcell( Line,2, j["text"]) end -- Setup Log Display accounts[acc].log_tab=iup.vbox { ["tabtitle"] =L.LogTab, accounts[acc].logtable, iup.fill{} } -- Top Level Panels -- accounts[acc].world_zbox = iup.zbox{} -- display main panel containing worlds (servers) -- not used ATM accounts[acc].mode_zbox = iup.zbox{} -- display submain panel containing tabs and dungeons accounts[acc].char_tabs = iup.tabs{} -- Top level of Char_Tabs, Character Info in Here accounts[acc].dung_tabs = iup.tabs{} -- Top level of Dung_Tabs, Dungeon Info in Here iup.Append(accounts[acc].mode_zbox, accounts[acc].char_tabs) detail_name = iup.label {title="",expand = "HORIZONTAL"} detail_desc = iup.label {title="",expand = "HORIZONTAL"} Status_bar = iup.label{title=L.Welcome .. " " .. L.Version .. " " .. version .. ".", expand = "HORIZONTAL"} iup.Append(accounts[acc].mode_zbox, accounts[acc].dung_tabs) -- Mode Buttons (Toggles) --[[ These control the display. Char mode lists the characters and information for them (default for prior versions) Dung Mode lists the dungeons and which characters have done them. Buttons are arranged in radio mode --]] accounts[acc].char_tog = iup.toggle{ title = L.Characters} accounts[acc].dung_tog = iup.toggle{ title = L.Dungeons} accounts[acc].view_tog = iup.toggle{ title = L.View_Toggle, VISIBLE = "NO"} local tog = accounts[acc].char_tog function tog:action(x) if x == 1 then accounts[acc].mode_zbox.value =accounts[acc].char_tabs iup.SetAttribute(accounts[acc].view_tog, "VISIBLE", "NO") end end tog = accounts[acc].dung_tog function tog:action(x) if x == 1 then accounts[acc].mode_zbox.value = accounts[acc].dung_tabs iup.SetAttribute(accounts[acc].view_tog, "VISIBLE", "YES") end end accounts[acc].mode = iup.frame { iup.hbox{ iup.radio { iup.hbox{ accounts[acc].char_tog, accounts[acc].dung_tog, }, }, accounts[acc].view_tog, } } accounts[acc].mode.title = L.Mode accounts[acc].mode.margin = "15x5" accounts[acc].alldungeons = {} -- Prepare for Dungeon data recording as we iterate through characters. accounts[acc].dung = {} -- put all dungeon mode stuff here. Populate it with character data. -- N Normal, V Vet, VH Vet hard mode dung = accounts[acc].dung dung.pub = {} dung.pub.box = {} dung.pub.key = {} dung.pub.name = "pub" table.insert(accounts[acc].alldungeons,dung.pub) dung.DLC = {} dung.DLC.box = {} dung.DLC.key = {} dung.DLC.name = "DLC" table.insert(accounts[acc].alldungeons,dung.DLC) dung.Grp = {} -- these ones are indexed. dung.Trials = {} tog = accounts[acc].view_tog function tog:action(x) if x == 1 then --hide completed columns for _, ADung in pairs (accounts[acc].alldungeons) do -- for each dungeon if (ADung.ShowColumn == nil) then print ("ADung.ShowColumn is nil for " .. ADung.name) break end for col,show in pairs(ADung.ShowColumn) do if show then iup.SetAttribute(ADung.box, "WIDTH"..tostring(col) ,"100") else iup.SetAttribute(ADung.box, "WIDTH"..tostring(col) ,"0") end end --]] end else -- show all for _, ADung in pairs (accounts[acc].alldungeons) do -- for each dungeon if (ADung.ShowColumn == nil) then print ("ADung.ShowColumn is nil for " .. ADung.name) break end for col,show in pairs(ADung.ShowColumn) do iup.SetAttribute(ADung.box, "WIDTH"..tostring(col) ,"100") end end end end -- Set up dungeon mode Group Dungeons for _,i in ipairs(Grp_Order) do dung.Grp[i]= {} dung.Grp[i].name = "Grp: " .. L.Grp_TabName[i] dung.Grp[i].key ={} -- key lookup dung.Grp[i].box = iup.matrix {numcol=#accounts[acc].playerIDs, numlin=_size(Grp_Dat[i].id), widthdef=100} iup.SetAttribute(dung.Grp[i].box, "READONLY", "YES") dung.Grp[i].tab = iup.vbox { ["tabtitle"] =L.Grp_TabName[i], dung.Grp[i].box, iup.fill{}, } -- Mouseover dung.Grp[i].box.dat = Grp_Dat[i] -- dung.Grp[i].box.mousemove_cb = box_mousemove_cb -- dung.Grp[i].box.leavewindow_cb = box_leavewindow_cb --set lines Heading dung.Grp[i].box:setcell(0,0, L.Location) --Set Line titles for line,key in ipairs(Grp_Dat[i].key) do dung.Grp[i].box:setcell(line, 0, grp_names[key]) end --Create Columns for Chars for col ,playerID in ipairs(accounts[acc].playerIDs) do dung.Grp[i].box:setcell(0, col, playerNames[playerID]) end table.insert(accounts[acc].alldungeons,dung.Grp[i]) end -- a table for each dungeon to which we add characters for _,i in ipairs(Grp1_Order) do for _,key in ipairs(grp1tokey) do dung.Grp[i].key[key] = {} for _,playerID in ipairs(accounts[acc].playerIDs) do dung.Grp[i].key[key][playerID] = false end end end for _,i in ipairs(Grp2_Order) do for _,key in ipairs(grp2tokey) do dung.Grp[i].key[key] = {} for _,playerID in ipairs(accounts[acc].playerIDs) do dung.Grp[i].key[key][playerID] = false end end end -- Set up dungeon mode Trials for _,i in ipairs(Trials_Order) do dung.Trials[i]= {} dung.Trials[i].name = L.Trial_TabName[i] dung.Trials[i].key ={} -- key lookup dung.Trials[i].box = iup.matrix {numcol=#accounts[acc].playerIDs, numlin=_size(Trials_Dat[i].id), widthdef=100} iup.SetAttribute(dung.Trials[i].box, "READONLY", "YES") dung.Trials[i].tab = iup.vbox { ["tabtitle"] =L.Trial_TabName[i], dung.Trials[i].box, iup.fill{}, } dung.Trials[i].box.dat = Trials_Dat[i] -- dung.Trials[i].box.mousemove_cb = box_mousemove_cb dung.Trials[i].box.leavewindow_cb = box_leavewindow_cb --set lines Heading dung.Trials[i].box:setcell(0,0, L.Location) --Set Line titles for line,key in ipairs(Trials_Dat[i].key) do dung.Trials[i].box:setcell(line, 0, Trials_Names[i][key]) end --Create Columns for Chars for col ,playerID in ipairs(accounts[acc].playerIDs) do dung.Trials[i].box:setcell(0, col, playerNames[playerID]) end -- a table for each dungeon to which we add characters for _,key in ipairs(Trials2key[i]) do dung.Trials[i].key[key] = {} for _,playerID in ipairs(accounts[acc].playerIDs) do dung.Trials[i].key[key][playerID] = false end end table.insert(accounts[acc].alldungeons,dung.Trials[i]) end -- for _,i in ipairs(Pub_Dat_Char.key) do -- dung.pub.key[i] = {} -- end for _,i in ipairs(DLC2key) do dung.DLC.key[i] = {} end -- ================ END Accountwide Data --================= START OF CHARACTER MODE DISPLAY -- Creates boxes, stage from names to allow sorting for _,playerID in ipairs(accounts[acc].playerIDs) do local me = accounts[acc].player[playerID] -- shorter reference: our code local thischar = History_SV["Default"][acc]["$AccountWide"]["data"][playerID] -- shorter reference: History DB -- Generate the leveling box. ============================ me.leveling_box = iup.matrix {numcol=6, numcol_visible=6, widthdef=60} me.leveling_box:setcell(0,1, L.Level) me.leveling_box:setcell(0,2, L.PTime) me.leveling_box:setcell(0,3, L.Start) me.leveling_box:setcell(0,4, L.Deaths) me.leveling_box:setcell(0,5, L.APts) me.leveling_box:setcell(0,6, L.Location) iup.SetAttribute(me.leveling_box, "WIDTH6", "100") iup.SetAttribute(me.leveling_box, "READONLY", "YES") -- levels as stored are unsorted, so create a level table which is sorted, local levels = {} for i,_ in pairs(thischar.levels) do table.insert(levels, i) end table.sort(levels) for i,j in ipairs(levels) do -- traverse in sorted order local timelevel = math.floor(thischar.levels[j].time) me.leveling_box.numlin = i me.leveling_box:setcell(i,1, j) me.leveling_box:setcell(i,2, math.floor(timelevel/60)) me.leveling_box:setcell(i,3, os.date("%Y-%m-%d",thischar.levels[j].begin)) me.leveling_box:setcell(i,4, thischar.levels[j].deaths) me.leveling_box:setcell(i,5, thischar.levels[j].Ach_Points) -- Do we have map name for this level? if thischar.levels[j].map ~= nil then me.leveling_box:setcell(i,6, thischar.levels[j].map) end end -- Create Grp Dungeon Boxes ==================================== me.Grp ={} -- Put them all together for _, i in ipairs(Grp_Order) do -- For Each Grp Dungeon me.Grp[i] = {} -- Dungeon data storage me.Grp[i].vet = Grp_Dat[i].vet me.Grp[i].box = iup.matrix {numcol=4, numcol_visible=4, numlin=Grp_Dat[i].lines, widthdef=100} iup.SetAttribute(me.Grp[i].box, "READONLY", "YES") me.Grp[i].box.ach = thischar.ach -- Put the Achievements here so the mouseover can get the users details me.Grp[i].box.dat = Grp_Dat[i] -- for mouseover me.Grp[i].box.mousemove_cb = box_mousemove_cb me.Grp[i].box.leavewindow_cb = box_leavewindow_cb --Set Column titles in box for j=1, 4 do me.Grp[i].box:setcell(0,j, Area_names[j].long) end -- set background to red -- iup.SetAttribute(me.Grp[i].box, "BGCOLOR", BG_Colour_Not_Complete) -- set text to black if achievement found. for id, Gdat in pairs (Grp_Dat[i].id) do local bgcolour,key if thischar.ach[id] ~= nil then bgcolour = "BGCOLOR" .. Gdat.L .. ":" .. Gdat.C iup.SetAttribute(me.Grp[i].box, bgcolour, BG_Colour_Complete) -- Add char to dungeon key = tostring(Gdat.L .. Gdat.C) if dung.Grp[i].key[key] == nil then print ("dung.Grp[i].key[key] key: " .. key .. " is nil.") end dung.Grp[i].key[key][playerID] = true else bgcolour = "BGCOLOR" .. Gdat.L .. ":" .. Gdat.C iup.SetAttribute(me.Grp[i].box, bgcolour, BG_Colour_Not_Complete) end end -- Create display tab me.Grp[i].tab = iup.vbox { ["tabtitle"] =L.Grp_TabName[i], me.Grp[i].box, iup.fill{}, } end -- these IDs are in Specials.lua --Set background of heading if all done if thischar.ach[1073] ~= nil then --EP Vanquisher iup.SetAttribute(me.Grp["1N"].box, "BGCOLOR0:1", Colour_Heading_Complete) end if thischar.ach[1074] ~= nil then --DC Vanquisher iup.SetAttribute(me.Grp["1N"].box , "BGCOLOR0:2", Colour_Heading_Complete) end if thischar.ach[1075] ~= nil then --AD Vanquisher iup.SetAttribute(me.Grp["1N"].box , "BGCOLOR0:3", Colour_Heading_Complete) end for _,i in ipairs(Grp_Order) do for _, id in pairs (Grp_Dat[i].id) do local key = tostring(id.L).. tostring(id.C) -- make name key me.Grp[i].box:setcell(id.L, id.C, grp_names[key]) end end -- Create Trials Dungeon Boxes ==================================== me.Trials ={} -- Put them all together for _, i in ipairs(Trials_Order) do -- For Each Dungeon me.Trials[i] = {} -- Dungeon data storage me.Trials[i].vet = Trials_Dat[i].vet me.Trials[i].box = iup.matrix {numcol=1, numcol_visible=1, numlin=_size(Trials_Dat[i].id), widthdef=110} me.Trials[i].box.ach = thischar.ach -- Put the Achievements here so the mouseover can get the users details me.Trials[i].box.dat = Trials_Dat[i] -- for mouseover me.Trials[i].box.mousemove_cb = box_mousemove_cb me.Trials[i].box.leavewindow_cb = box_leavewindow_cb --Set Column titles in box for line,key in ipairs (Trials2key[i]) do -- Load Dungeons Name. Info LC is the Dungeon Identifier me.Trials[i].box:setcell(line,0, Trials_Names[i][key]) end iup.SetAttribute(me.Trials[i].box, "WIDTH0", "170") -- Ach Description, is Col 0 iup.SetAttribute(me.Trials[i].box, "BGCOLOR*:1", BG_Colour_Not_Complete) --iup.SetAttribute(me.Trials[i].box, "FGCOLOR*:1", "DEFAULT") -- set text if achievement found and change background for id, Gdat in pairs (Trials_Dat[i].id) do local bgcolour if thischar.ach[id] ~= nil then bgcolour = "BGCOLOR" .. Gdat.L .. ":" .. Gdat.C me.Trials[i].box:setcell(Gdat.L,Gdat.C, L.YesLabel) iup.SetAttribute(me.Trials[i].box, bgcolour, BG_Colour_Complete) -- Add char to dungeon dung.Trials[i].key[Gdat.key][playerID] = true else me.Trials[i].box:setcell(Gdat.L,Gdat.C, L.NoLabel) end end -- Create display tab me.Trials[i].tab = iup.vbox { ["tabtitle"] =L.Trial_TabName[i], me.Trials[i].box, iup.fill{}, } end -- Create Pub Dungeon Achievements Box========================== me.Pub_box = iup.matrix {READONLY="YES",numcol=4, numcol_visible=4, numlin=5, widthdef=100} iup.SetAttribute(me.Pub_box, "READONLY", "YES") me.Pub_box.dat = Pub_Dat_Char me.Pub_box.ach = thischar.ach me.Pub_box.mousemove_cb = box_mousemove_cb me.Pub_box.leavewindow_cb = box_leavewindow_cb for i=1, 4 do -- Load text me.Pub_box:setcell(0,i, Area_names[i].long) end iup.SetAttribute(me.Pub_box, "BGCOLOR" , BG_Colour_Not_Complete) for id,_ in pairs (Pub_Dat_Char.id) do local bgcolour = "BGCOLOR" .. Pub_Dat_Char.id[id].L .. ":" .. Pub_Dat_Char.id[id].C if thischar.ach[id] ~= nil then iup.SetAttribute(me.Pub_box, bgcolour, BG_Colour_Complete) -- Add char to dungeon local key = tostring(Pub_Dat_Char.id[id].L .. Pub_Dat_Char.id[id].C) if dung.pub.key[key] == nil then -- Add if needed dung.pub.key[key] = {} end dung.pub.key[key][playerID] = true else iup.SetAttribute(me.Pub_box, bgcolour, BG_Colour_Not_Complete) end end if thischar.ach[1068] ~= nil then --EP Conqueror iup.SetAttribute(me.Pub_box, "BGCOLOR0:1", Colour_Heading_Complete) end if thischar.ach[1070] ~= nil then --DC Conqueror iup.SetAttribute(me.Pub_box, "BGCOLOR0:2", Colour_Heading_Complete) end if thischar.ach[1069] ~= nil then --AD Conqueror iup.SetAttribute(me.Pub_box, "BGCOLOR0:3", Colour_Heading_Complete) end for id,dat in pairs (Pub_Dat_Char.id) do -- Load text local key = tostring(tostring(dat.L) .. tostring(dat.C)) -- make name key local dname = pub_names[key] if dname == nil then dname = "key " .. key .." not found in pub_names" end me.Pub_box:setcell(dat.L,dat.C,dname) end -- Create Locations Box============================================== me.Map_box= iup.matrix {numcol=6, numcol_visible=6, numlin=0, widthdef=70} me.Map_box:setcell(0,0, L.Location) me.Map_box:setcell(0,1, L.Visits) me.Map_box:setcell(0,2, L.FirstVisited) me.Map_box:setcell(0,3, L.FirstLevel) me.Map_box:setcell(0,4, L.TimesLeveled) me.Map_box:setcell(0,5, L.FirstDeath) me.Map_box:setcell(0,6, L.Deaths) iup.SetAttribute(me.Map_box, "READONLY", "YES") iup.SetAttribute(me.Map_box, "ALIGNMENT0", "ALEFT") iup.SetAttribute(me.Map_box, "WIDTH0", "100") iup.SetAttribute(me.Map_box, "WIDTH1", "40") iup.SetAttribute(me.Map_box, "WIDTH4", "55") iup.SetAttribute(me.Map_box, "WIDTH6", "40") local map_names = {} for map,_ in pairs(thischar.maps) do table.insert(map_names,map) end table.sort(map_names) local Line =1 for _, map in ipairs(map_names) do me.Map_box.numlin = Line me.Map_box:setcell( Line,0, map) if thischar.maps[map].visit ~= nil then me.Map_box:setcell( Line,1, thischar.maps[map].visit) end if thischar.maps[map].firstvisitdate ~= nil then local firstvisit = os.date(dateformat,thischar.maps[map].firstvisitdate) me.Map_box:setcell( Line,2, firstvisit) end if thischar.maps[map].firstlevel ~= nil then me.Map_box:setcell( Line,3, thischar.maps[map].firstlevel) end if thischar.maps[map].timeslevel ~= nil then me.Map_box:setcell( Line,4, thischar.maps[map].timeslevel) end if thischar.maps[map].firstdeathlevel ~= nil then me.Map_box:setcell( Line,5, thischar.maps[map].firstdeathlevel) end if thischar.maps[map].deaths ~= nil then me.Map_box:setcell( Line,6, thischar.maps[map].deaths ) end Line= Line +1 end -- Create WorldBoss Achievements Box========================== me.WB_box= Location_Box() print("Done WB Box") Populate_Dat(me.WB_box, WB_dat,me.ach) -- Create SkillQuest Achievements Box========================== me.SQ_box= Location_Box() Populate_Dat(me.SQ_box, SQ_dat,me.ach) --========== DLC me.DLC_box= iup.matrix {numcol=7, numcol_visible=7, numlin=4, widthdef=115} iup.SetAttribute(me.DLC_box, "READONLY", "YES") me.DLC_box.dat = DLC_Dat me.DLC_box.ach = thischar.ach me.DLC_box.mousemove_cb = box_mousemove_cb me.DLC_box.leavewindow_cb = box_leavewindow_cb --Set Column titles me.DLC_box:setcell(0,1, Area_names[6].long) -- Orsinium me.DLC_box:setcell(0,2, Area_names[8].long) -- IC me.DLC_box:setcell(0,3, Area_names[9].long) -- Hist me.DLC_box:setcell(0,4, Area_names[10].long) -- Horns me.DLC_box:setcell(0,5, Area_names[11].long) -- Bones -- me.DLC_box:setcell(0,6, Area_names[12].long) -- VVardenfell me.DLC_box:setcell(0,6, Area_names[14].long) -- Wolf me.DLC_box:setcell(0,7, Area_names[15].long) -- Murk for id,_ in pairs (DLC_Dat.id) do local L = DLC_Dat.id[id].L local C = DLC_Dat.id[id].C local key = tostring(L).. tostring(C) -- make name key me.DLC_box:setcell(L, C, DLC_Location_names[key]) end -- set text to black and bg to green if achievement found. for id,_ in pairs (DLC_Dat.id) do local bgcolour = "BGCOLOR" .. DLC_Dat.id[id].L .. ":" .. DLC_Dat.id[id].C if thischar.ach[id] ~= nil then iup.SetAttribute(me.DLC_box, bgcolour, BG_Colour_Complete) -- Add char to dungeon key = tostring(DLC_Dat.id[id].L .. DLC_Dat.id[id].C) dung.DLC.key[key][playerID] = true else iup.SetAttribute(me.DLC_box, bgcolour, BG_Colour_Not_Complete) end end if thischar.ach[1248] ~= nil then --"Hero of Wrothgar", iup.SetAttribute(me.DLC_box, "BGCOLOR0:1", Colour_Heading_Complete) end me.DLC2 = {} me.DLC2_tabs = iup.flattabs{} -- we add our tabs to here for display. (list of vboxes) local wrap_size = math.floor(250/3.7) -- print ("wrap_size: " .. wrap_size) for i,dlc in ipairs (DLC_Order) do me.DLC2[dlc] = {} me.DLC2[dlc].box = iup.matrixex {READONLY="YES", numcol=4, numcol_visible=4, numlin=#DLC_Dat2[dlc].line} iup.SetAttribute(me.DLC2[dlc].box,"WIDTH1", 50) iup.SetAttribute(me.DLC2[dlc].box,"WIDTH2", 130) iup.SetAttribute(me.DLC2[dlc].box,"WIDTH3", 250) --Size is about 1/4 of character iup.SetAttribute(me.DLC2[dlc].box,"ALIGNMENT1", "ACENTER") iup.SetAttribute(me.DLC2[dlc].box,"ALIGNMENT2", "ALEFT") iup.SetAttribute(me.DLC2[dlc].box,"ALIGNMENT3", "ALEFT") iup.SetAttribute(me.DLC2[dlc].box,"ALIGNMENT4", "ALEFT") me.DLC2[dlc].box:setcell(0, 1, L.Ach_ID) me.DLC2[dlc].box:setcell(0, 2, L.Achievement) me.DLC2[dlc].box:setcell(0, 4, L.Completed) me.DLC2[dlc].box.name = dlc2 -- Filter for text on DLC2 me.DLC2[dlc].filter_l = iup.list{editbox="YES", SIZE="80x60"} me.DLC2[dlc].filter_r = iup.list{editbox="YES", SIZE="80x60"} me.DLC2[dlc].filter_tog = iup.toggle{title=L.Filter} me.DLC2[dlc].filter_vet = iup.toggle{title=L.Vet} me.DLC2[dlc].filter_vanq = iup.toggle{title=L.Vanquisher} me.DLC2[dlc].filter_conq = iup.toggle{title=L.Conqueror} me.DLC2[dlc].filter_f = iup.frame { iup.hbox{ me.DLC2[dlc].filter_l, iup.space{size=20}, me.DLC2[dlc].filter_r, iup.space{size=20}, iup.vbox { me.DLC2[dlc].filter_tog, me.DLC2[dlc].filter_vet, me.DLC2[dlc].filter_vanq, me.DLC2[dlc].filter_conq, }, }, } me.DLC2[dlc].filter_f.title = L.Filter me.DLC2[dlc].filter_f.margin = "15x5" me.DLC2[dlc].filter = function (v) -- vi is 1 or 0 for l =1, #DLC_Dat2[dlc].line do print("Get:" .. me.DLC2[dlc].box:getcell(l, 3)) if v == 1 then if string.find (me.DLC2[dlc].box:getcell(l, 3), L.Vet) ~= nil then iup.SetAttribute(me.DLC2[dlc].box,"VISIBLELIN" .. tostring(l) , "NO") else iup.SetAttribute(me.DLC2[dlc].box,"VISIBLELIN" .. tostring(l) , "YES") end else iup.SetAttribute(me.DLC2[dlc].box,"VISIBLELIN" .. tostring(l) , "YES") end end end local thistog=me.DLC2[dlc].filter_vet function thistog:action(v) me.DLC2[dlc].filter(v) end --Add data for line,id in ipairs(DLC_Dat2[dlc].line) do if Ach_Detail[id] == nil then print("Ach id: " .. id .. " in DLC but not in master data.") break end me.DLC2[dlc].box:setcell(line, 1, tostring(id)) me.DLC2[dlc].box:setcell(line, 2, Ach_Detail[id].name) local split = split_w(Ach_Detail[id].description) -- Split into array of words local flow = flow_w(split, wrap_size) -- print(join_s(flow)) -- print("") me.DLC2[dlc].box:setcell(line, 3, join_s(flow)) iup.SetAttribute(me.DLC2[dlc].box,"FITTOTEXT", "L".. tostring(line)) local bgcolour1 = "BGCOLOR" .. tostring(line) .. ":1" --Detail and Description Columns local bgcolour2 = "BGCOLOR" .. tostring(line) .. ":2" local bgcolour3 = "BGCOLOR" .. tostring(line) .. ":3" local bgcolour4 = "BGCOLOR" .. tostring(line) .. ":4" if thischar.ach[id] ~= nil then iup.SetAttribute(me.DLC2[dlc].box, bgcolour1, BG_Colour_Complete) iup.SetAttribute(me.DLC2[dlc].box, bgcolour2, BG_Colour_Complete) iup.SetAttribute(me.DLC2[dlc].box, bgcolour3, BG_Colour_Complete) iup.SetAttribute(me.DLC2[dlc].box, bgcolour4, BG_Colour_Complete) me.DLC2[dlc].box:setcell(line, 4, os.date(dateformat,thischar.ach[id].time)) -- Add char to dungeon -- key = tostring(DLC_Dat.id[id].L .. DLC_Dat.id[id].C) -- dung.DLC.key[key][playerID] = true else iup.SetAttribute(me.DLC2[dlc].box, bgcolour1, BG_Colour_Not_Complete) iup.SetAttribute(me.DLC2[dlc].box, bgcolour2, BG_Colour_Not_Complete) iup.SetAttribute(me.DLC2[dlc].box, bgcolour3, BG_Colour_Not_Complete) iup.SetAttribute(me.DLC2[dlc].box, bgcolour4, BG_Colour_Not_Complete) end end --lines in box -- make a tab out that DLC. me.DLC2[dlc].tab = iup.vbox{ iup.hbox{ me.DLC2[dlc].box, me.DLC2[dlc].filter_f, }, iup.fill{} } me.DLC2[dlc].tab.tabtitle=DLC_Names[i] --Check for Special Completion if (DLC_Dat2[dlc].complete ~= nil and thischar.ach[DLC_Dat2[dlc].complete]) then -- print(me.name .. " Complete.") end iup.Append(me.DLC2_tabs,me.DLC2[dlc].tab) --Accumulate here for display end -- ==================================== -- == Prepare for the character data display tabs me.tab = iup.vbox{ ["tabtitle"] = me.name, -- This vbox will be a tab and the tab text is this iup.hbox{ --Top Information bar Alignment = "ACENTER", iup.label{title=thischar.world,PADDING="10X0"}, iup.label{title=me.gender, FONT="Times,BOLD,10"}, iup.label{title=thischar.Race .." / ".. thischar.Class, PADDING="10X0", FONT="Times,BOLD,10"}, iup.label{title=thischar.Alliance, PADDING="10X0"}, iup.label{title=L.Level .. ": ".. me.levelstr, PADDING="10X0"}, iup.label{title=L.Created .. os.date(dateformat,thischar.Created), PADDING="10X0"}, iup.label{title=L.LLog .. os.date(dateformat,thischar.LoginTime), PADDING="10X0"}, iup.label{title=L.TPlayed .. me.timeplayed .." " .. L.Hrs}, iup.fill{} }, iup.label{SEPARATOR="HORIZONTAL"} } me.data_tabs = iup.tabs{} --Data tabs for Char -- All Grp Dungeons for _,i in ipairs (Grp_Order) do if me.isvet or me.Grp[i].vet == false then -- non vet chars only see non-vet dungeons iup.Append(me.data_tabs, me.Grp[i].tab) end end -- All Trials Dungeons for _,i in ipairs (Trials_Order) do if me.isvet or me.Trials[i].vet == false then -- non vet chars only see non-vet dungeons iup.Append(me.data_tabs, me.Trials[i].tab) end end iup.Append(me.data_tabs, iup.vbox { ["tabtitle"] =L.PubDungeon, iup.label{title=L.PubLab,expand="HORIZONTAL"}, me.Pub_box, iup.fill{} }) if me.isvet then --[[ iup.Append(me.data_tabs, iup.vbox { ["tabtitle"] =L.VetDungeon, iup.label{title=L.VetLab,expand="HORIZONTAL"}, me.Vet_box, iup.fill{} }) --]] end iup.Append(me.data_tabs, iup.vbox { ["tabtitle"] =L.Leveling, -- iup.label{title="LevLabel",expand="HORIZONTAL"}, me.leveling_box, iup.fill{} }) iup.Append(me.data_tabs, iup.vbox { ["tabtitle"] =L.Locations, -- iup.label{title="LevLabel",expand="HORIZONTAL"}, me.Map_box, iup.fill{} }) iup.Append(me.data_tabs, iup.vbox { ["tabtitle"] =L.WBosses, iup.label{title=L.WBLab,expand="HORIZONTAL"}, me.WB_box, iup.label{title=L.WB_Detail}, me.WB_box.Detail_zbox, iup.fill{} }) iup.Append(me.data_tabs, iup.vbox { ["tabtitle"] =L.SkillQuests, iup.label{title=L.SkillLab,expand="HORIZONTAL"}, me.SQ_box, iup.label{title=L.SQ_Detail}, me.SQ_box.Detail_zbox, iup.fill{} }) iup.Append(me.data_tabs, iup.vbox { ["tabtitle"] =L.DLC, iup.label{title=L.DLCLab,expand="HORIZONTAL"}, me.DLC_box, iup.fill{} }) iup.Append(me.data_tabs, iup.vbox { ["tabtitle"] ="DLC2", iup.label{title=L.DLCLab,expand="HORIZONTAL"}, me.DLC2_tabs, iup.fill{}, }) iup.Append(me.tab,me.data_tabs) -- Add Dungeons/Data under the Character iup.Append(accounts[acc].char_tabs,me.tab) -- Add Char tab to Account local wide =((#accounts[acc].playerIDs+1) * 110) if wide < 690 then wide = 690 elseif wide >960 then wide = 960 end accounts[acc].panelsize = tostring(wide) .. "x350" end -- Chars -- Add to end of Characters iup.Append(accounts[acc].char_tabs, accounts[acc].log_tab) --================= END OF CHARACTER MODE DISPLAY --================= START OF DUNGEON MODE DISPLAY -- Generic function for populating these tables populate = function(ADung,Grp_key) if ADung.key == nil then print ("ADung.key is nil (fatal)") end ADung.ShowColumn = {} -- Save Column Completion Information -- Set Column Show Information to false for col,playerID in ipairs(accounts[acc].playerIDs) do ADung.ShowColumn[col] = false end for line, key in ipairs(Grp_key) do -- for lines going down, get the key -- does that char exist in the table. Check by PlayerID for col,playerID in ipairs(accounts[acc].playerIDs) do -- over each char in order if ADung.key[key] == nil then ADung.key[key] = {} end if ADung.key[key][playerID] then ADung.box:setcell(line,col, L.YesLabel) iup.SetAttribute(ADung.box,"BGCOLOR" .. tostring(line) .. ":" .. tostring(col), BG_Colour_Complete) else ADung.box:setcell(line,col, L.NoLabel) iup.SetAttribute(ADung.box,"BGCOLOR" .. tostring(line) .. ":" .. tostring(col), BG_Colour_Not_Complete) ADung.ShowColumn[col] = true -- flag entire column as not complete, thus to show it. end end end --Ok, Set the Column Width flag Hide sometimes --And column Heading background Always for col,state in pairs(ADung.ShowColumn) do if state then iup.SetAttribute(ADung.box,"BGCOLOR" .. "0:" .. tostring(col), BG_Colour_Not_Complete) else iup.SetAttribute(ADung.box,"BGCOLOR" .. "0:" .. tostring(col), BG_Colour_Complete) end end end -- Create Pub Dungeon Character Box========================= dung.pub.box = iup.matrix {numcol=#accounts[acc].playerIDs, numlin=#Pub_Dat_Char.key, widthdef=100} dung.pub.box.dat = Pub_Dat_Char -- dung.pub.box.mousemove_cb = box_mousemove_cb dung.pub.box.leavewindow_cb = box_leavewindow_cb --Set Line titles for line,key in ipairs(Pub_Dat_Char.key) do dung.pub.box:setcell(line, 0, pub_names[key]) end --set lines dung.pub.box:setcell(0,0, L.Location) --Create Columns for Chars for col ,playerID in ipairs(accounts[acc].playerIDs) do dung.pub.box:setcell(0, col, playerNames[playerID]) end iup.SetAttribute(dung.pub.box, "READONLY", "YES") -- Populate with character data ============================ -- print ("Populating Pub") populate(dung.pub,Pub_Dat_Char.key) -- Create Pub Dungeon Tab ================================== dung.pub.tab = iup.vbox { ["tabtitle"] =L.Pub, dung.pub.box, iup.fill{}, } iup.Append(accounts[acc].dung_tabs, dung.pub.tab) -- Grp Dungeons =========================================== for _,i in ipairs (Grp_Order) do iup.Append(accounts[acc].dung_tabs, dung.Grp[i].tab) -- Populate with character data ============================ -- print ("populate Grp,i: " .. i) populate(dung.Grp[i], Grp_Dat[i].key) end -- Create DLC Dungeon Character Box========================= dung.DLC.box = iup.matrix {numcol=#accounts[acc].playerIDs , numlin=#DLC2key, widthdef=100} dung.DLC.box.dat = DLC_Dat -- dung.DLC.box.mousemove_cb = box_mousemove_cb dung.DLC.box.leavewindow_cb = box_leavewindow_cb --Set Line titles for i, key in ipairs(DLC2key) do dung.DLC.box:setcell(i, 0, DLC_Location_names[key]) end --set lines dung.DLC.box:setcell(0,0, L.Location) --Create Columns for Chars for i,playerID in ipairs(accounts[acc].playerIDs ) do dung.DLC.box:setcell(0, i, playerNames[playerID]) end iup.SetAttribute(dung.DLC.box, "READONLY", "YES") populate(dung.DLC,DLC_Dat.key) -- Create DLC Dungeon Tab ================================== dung.DLC.tab = iup.vbox { ["tabtitle"] =L.DLC, dung.DLC.box, iup.fill{}, } iup.Append(accounts[acc].dung_tabs, dung.DLC.tab) -- Commented out because we expect all dung to be populated -- if #accounts[acc].playerIDs_vet > 0 then -- skip vet and trials if no eligible chars -- Create Trials Tab ============================================ for _,i in ipairs (Trials_Order) do iup.Append(accounts[acc].dung_tabs, dung.Trials[i].tab) -- Populate with character data ============================ -- print ("populate Trials") populate(dung.Trials[i], Trials_Dat[i].key) end --end -- has vet chars end -- Accounts table.sort(accounts_list) function select_account() local selected if #accounts_list > 1 then selected = iup.ListDialog (1, L.SelectA, #accounts_list, --Size accounts_list, 1, --Initial 1,#accounts_list --MaxCol MaxLine ) if selected <0 then return nil -- Canceled iup.SetAttribute(ADung.box,"BGCOLOR" .. "0:" .. tostring(col), BG_Colour_Not_Complete) else return accounts_list[selected+1] end else return accounts_list[1] -- only 1 account, no need for Dialog end end -- Create dialog to choose account myaccount=select_account() if myaccount ~=nil then -- Create dialog if not cancelled dlg = iup.dialog{iup.vbox{ accounts[myaccount].mode, accounts[myaccount].mode_zbox, detail_name, -- Hover over information detail_desc, Status_bar, -- Bottom Status bar. margin="5x5", ngap="3", }, title=L.title .. myaccount , size=accounts[myaccount].panelsize, } -- Shows dialog in the centre of the screen dlg:showxy(iup.CENTER, iup.CENTER) if (iup.MainLoopLevel()==0) then iup.MainLoop() end end