Mercurial > wow > buffalo2
comparison ObjectiveUI.lua @ 8:7923243ae972
ObjectiveUI & ObjectiveEvents
- securehook to API calls for compatibility with addons that work with the objective tracking interface
- let the API hooks invoke ObjectiveUI functions when possible
- ObjectiveUI framescript handlers should use the corresponding API call if possible, so that addon space can be fully aware of our actions
- Sanity check cached data when possible during 'Remove' hooks
ObjectiveInfo
- Add cheevID to criteria info
ObjectiveCore
- Index quest tracker blocks by their watch offset, and use that to verify whether the given block frame should be released into pool
ObjectiveFrame
- Differentiate between visible and non-visible unused buttons, and only release when their quest has been dropped
| author | Nenue |
|---|---|
| date | Fri, 01 Apr 2016 14:40:14 -0400 |
| parents | 5301c68f28d8 |
| children | 2698173edd40 |
comparison
equal
deleted
inserted
replaced
| 7:5301c68f28d8 | 8:7923243ae972 |
|---|---|
| 34 self:Open() | 34 self:Open() |
| 35 end | 35 end |
| 36 self.initialButton = nil | 36 self.initialButton = nil |
| 37 self.modChatLink = nil | 37 self.modChatLink = nil |
| 38 self.modQuestWatch = nil | 38 self.modQuestWatch = nil |
| 39 print('|cFFFF8800'..tostring(self:GetName())..':MouseUp()|r ->',self.info.trackingID) | 39 print(IsModifiedClick("CHATLINK"), IsModifiedClick("QUESTWATCHTOGGLE")) |
| 40 print('|cFFFF8800'..tostring(self:GetName())..':MouseUp()|r') | |
| 40 end | 41 end |
| 41 | 42 |
| 42 Tracker.OnMouseDown = function(self, button) | 43 Tracker.OnMouseDown = function(self, button) |
| 43 self.initialButton = button | 44 self.initialButton = button |
| 44 self.modChatLink = IsModifiedClick("CHATLINK") | 45 self.modChatLink = IsModifiedClick("CHATLINK") |
| 45 self.modQuestWatch = IsModifiedClick("QUESTWATCHTOGGLE") | 46 self.modQuestWatch = IsModifiedClick("QUESTWATCHTOGGLE") |
| 46 self:SetStyle('Active') | 47 self:SetStyle('Active') |
| 48 print(IsModifiedClick("CHATLINK"), IsModifiedClick("QUESTWATCHTOGGLE")) | |
| 47 print(self.info.title) | 49 print(self.info.title) |
| 48 end | 50 end |
| 49 | 51 |
| 50 ----------------------------- | 52 ----------------------------- |
| 51 --- AUTO_QUEST | 53 --- AUTO_QUEST |
| 70 end | 72 end |
| 71 | 73 |
| 72 Quest.Remove = function(self) | 74 Quest.Remove = function(self) |
| 73 print('removing', self.info.questLogIndex, 'from watcher') | 75 print('removing', self.info.questLogIndex, 'from watcher') |
| 74 RemoveQuestWatch(self.info.questLogIndex) | 76 RemoveQuestWatch(self.info.questLogIndex) |
| 75 | |
| 76 mod.Quest.LogBlock[self.info.questLogIndex] = nil | |
| 77 mod.Quest.QuestBlock[self.info.questID] = nil | |
| 78 QuestPOIUpdateIcons() | |
| 79 mod.UpdateWrapper() | |
| 80 end | 77 end |
| 81 | 78 |
| 82 | 79 |
| 83 ----------------------------- | 80 ----------------------------- |
| 84 --- CHEEVS | 81 --- CHEEVS |
| 85 Cheevs.Select = function(self) | 82 Cheevs.Select = function(self) |
| 86 end | 83 end |
| 84 Cheevs.Remove = function(self) | |
| 85 RemoveTrackedAchievement(self.info.cheevID) | |
| 86 end | |
| 87 Cheevs.OnMouseUp = function(self) | |
| 88 Tracker.OnMouseUp(self) | |
| 89 self:SetStyle('CheevNormal') | |
| 90 end | |
| 87 Cheevs.Link = function(self) | 91 Cheevs.Link = function(self) |
| 88 local achievementLink = GetAchievementLink(self.info.cheevID); | 92 local achievementLink = GetAchievementLink(self.info.cheevID); |
| 89 if ( achievementLink ) then | 93 if ( achievementLink ) then |
| 90 ChatEdit_InsertLink(achievementLink); | 94 ChatEdit_InsertLink(achievementLink); |
| 91 end | 95 end |
| 92 self:SetStyle('CheevNormal') | |
| 93 end | 96 end |
| 94 | 97 |
| 95 Cheevs.Open = function(self) | 98 Cheevs.Open = function(self) |
| 96 if ( not AchievementFrame ) then | 99 if ( not AchievementFrame ) then |
| 97 AchievementFrame_LoadUI(); | 100 AchievementFrame_LoadUI(); |
| 247 local wr = mod.WidgetRegistry | 250 local wr = mod.WidgetRegistry |
| 248 | 251 |
| 249 --- Get a usable widget for the given achievement criteria set. | 252 --- Get a usable widget for the given achievement criteria set. |
| 250 -- Returns a frame object with dimensioning parameters needed to size the receiving tracker block | 253 -- Returns a frame object with dimensioning parameters needed to size the receiving tracker block |
| 251 mod.SetWidget = function(obj, info) | 254 mod.SetWidget = function(obj, info) |
| 255 local print = B.print('ObjectiveWidgets') | |
| 252 local widgetType = obj.type | 256 local widgetType = obj.type |
| 253 local widget | 257 local widget |
| 254 | 258 if wr[widgetType] and wr[widgetType].used[obj.criteriaID] then |
| 255 if not wr[widgetType] or #wr[widgetType].free == 0 then | 259 widget = wr[widgetType].used[obj.criteriaID] |
| 256 print('VeneerObjectiveCriteria' .. widgetType) | 260 print('|cFF00FF00Updating ('..obj.criteriaID..')', widget) |
| 257 widget = CreateFrame('Frame', nil, VeneerObjectiveScroll, 'VeneerObjectiveCriteria' .. widgetType) | 261 elseif not wr[widgetType] or #wr[widgetType].free == 0 then |
| 258 end | 262 widget = CreateFrame('Frame', 'VeneerObjective' .. widgetType .. (wr[widgetType] and (wr[widgetType].lastn+1) or (1)), VeneerObjectiveScroll, 'VeneerObjectiveCriteria' .. widgetType) |
| 259 local free = wr[widgetType].free | 263 |
| 260 local used = wr[widgetType].used | 264 print('|cFFFF0088Creating `'..widget:GetName()..'` id', wr[widgetType].lastn) |
| 261 | 265 else |
| 262 widget = tremove(free) | 266 widget = tremove(wr[widgetType].free) |
| 263 local index = #used+1 | 267 print('|cFFFFFF00Acquiring released widget', widget:GetName()) |
| 264 used[index] = widget | 268 end |
| 265 wr[widgetType].usedIndex[widget] = index | 269 |
| 270 wr[widgetType].used[obj.criteriaID] = widget | |
| 266 widget.info = obj | 271 widget.info = obj |
| 267 widget.parentInfo = info | 272 widget.parentInfo = info |
| 268 mod.InitializeWidget(widget) | 273 mod.InitializeWidget(widget) |
| 269 | |
| 270 return widget | 274 return widget |
| 271 end | 275 end |
| 272 | 276 |
| 273 --- Fired by OnLoad() when a new frame is spawned | 277 --- WidgetTemplate 'OnLoad' |
| 274 mod.RegisterWidget = function(frame) | 278 mod.RegisterWidget = function(frame) |
| 279 local print = B.print('ObjectiveWidgets') | |
| 275 local widgetType = frame.widgetType | 280 local widgetType = frame.widgetType |
| 276 local obj = frame.info | |
| 277 if not wr[frame.widgetType] then | 281 if not wr[frame.widgetType] then |
| 278 print('|cFFFF4400[[WidgetTemplate]]|r', widgetType) | 282 print('|cFFFF4400[[WidgetTemplate]]|r', widgetType) |
| 279 wr[widgetType] = { lastn = 0, free = {}, used = {}, usedIndex = {}, freeIndex = {} } | 283 wr[widgetType] = { lastn = 1, free = {}, used = {}, usedIndex = {}, freeIndex = {} } |
| 280 end | 284 else |
| 281 tinsert(wr[frame.widgetType].free, frame) | 285 print('|cFF0088FF+ [[WidgetTemplate]]r', widgetType, wr[widgetType].lastn) |
| 282 end | 286 wr[widgetType].lastn = wr[widgetType].lastn + 1 |
| 287 end | |
| 288 end | |
| 289 | |
| 290 --- WidgetTemplate 'OnShow' | |
| 283 mod.InitializeWidget = setmetatable({}, { | 291 mod.InitializeWidget = setmetatable({}, { |
| 284 __call = function(t, frame) | 292 __call = function(t, frame) |
| 285 -- todo: config pull | 293 -- todo: config pull |
| 286 local maxWidth = 250 | 294 local maxWidth = 250 |
| 287 | 295 |
| 299 frame:RegisterEvent('CRITERIA_EARNED') | 307 frame:RegisterEvent('CRITERIA_EARNED') |
| 300 | 308 |
| 301 return t[frame.widgetType](frame) | 309 return t[frame.widgetType](frame) |
| 302 end, | 310 end, |
| 303 }) | 311 }) |
| 312 | |
| 313 --- WidgetTemplate 'OnEvent' | |
| 304 mod.UpdateWidget = setmetatable({}, { | 314 mod.UpdateWidget = setmetatable({}, { |
| 305 __call = function(t, frame) | 315 __call = function(t, frame) |
| 306 if not frame.widgetType then | 316 if not frame.widgetType then |
| 307 error('Invalid widget template, needs .widgetType') | 317 error('Invalid widget template, needs .widgetType') |
| 308 return | 318 return |
| 310 | 320 |
| 311 return t[frame.widgetType](frame) | 321 return t[frame.widgetType](frame) |
| 312 end | 322 end |
| 313 }) | 323 }) |
| 314 | 324 |
| 325 --- WidgetTemplate 'OnHide' | |
| 315 mod.ReleaseWidget = function(frame) | 326 mod.ReleaseWidget = function(frame) |
| 327 local print = B.print('ObjectiveWidgets') | |
| 316 local reg = wr[frame.widgetType] | 328 local reg = wr[frame.widgetType] |
| 317 if reg and reg.usedIndex[frame] then | 329 if reg and reg.used[frame.info.criteriaID] then |
| 318 tremove(reg.used, reg.usedIndex[frame]) | 330 reg.used[frame.info.criteriaID] = nil |
| 319 reg.usedIndex[frame] = nil | 331 frame.info = nil |
| 332 frame.parentInfo = nil | |
| 320 frame:UnregisterAllEvents() | 333 frame:UnregisterAllEvents() |
| 321 tinsert(reg.free, frame) | 334 tinsert(reg.free, frame) |
| 335 print('|cFFBBBBBBreleased from service', frame:GetName()) | |
| 336 end | |
| 337 end | |
| 338 | |
| 339 --- RemoveTrackedAchievement post-hook | |
| 340 mod.CleanWidgets = function() | |
| 341 local print = B.print('ObjectiveWidgets') | |
| 342 local tracked = {GetTrackedAchievements() } | |
| 343 for type, reg in pairs(mod.WidgetRegistry) do | |
| 344 print('collecting', type) | |
| 345 for criteriaID, frame in pairs(reg.used) do | |
| 346 local id = frame.info.cheevID | |
| 347 | |
| 348 if id and not tContains(tracked, id) then | |
| 349 | |
| 350 print(' untracked achievement', id, 'associated with', criteriaID, frame:GetName()) | |
| 351 frame:Hide() | |
| 352 end | |
| 353 end | |
| 322 end | 354 end |
| 323 end | 355 end |
| 324 | 356 |
| 325 mod.WidgetParams = { | 357 mod.WidgetParams = { |
| 326 ['ProgressBar'] = { | 358 ['ProgressBar'] = { |
| 329 quantityString = {SetFontObject = _G.VeneerFontNormal} | 361 quantityString = {SetFontObject = _G.VeneerFontNormal} |
| 330 } | 362 } |
| 331 } | 363 } |
| 332 | 364 |
| 333 mod.InitializeWidget.ProgressBar = function(self) | 365 mod.InitializeWidget.ProgressBar = function(self) |
| 366 local print = B.print('ObjectiveWidgets') | |
| 334 local params = mod.WidgetParams[self.widgetType] | 367 local params = mod.WidgetParams[self.widgetType] |
| 335 self.height = params.height | 368 self.height = params.height |
| 336 self:SetHeight(20) | 369 self:SetHeight(20) |
| 337 self.bg:SetHeight(20) | 370 self.bg:SetHeight(20) |
| 338 self.fg:SetHeight(18) | 371 self.fg:SetHeight(16) |
| 339 self.fg:SetPoint('BOTTOMLEFT', self.bg, 'BOTTOMLEFT', 1, 1) | 372 self.fg:SetPoint('BOTTOMLEFT', self.bg, 'BOTTOMLEFT', 1, 1) |
| 340 self.quantityString:SetFontObject(params.quantityString.SetFontObject) | 373 self.quantityString:SetFontObject(params.quantityString.SetFontObject) |
| 341 self.quantityString:SetText(self.info.quantityString) | 374 self.quantityString:SetText(self.info.quantityString) |
| 342 end | 375 end |
| 343 | 376 |
| 344 mod.UpdateWidget.ProgressBar = function (self) | 377 mod.UpdateWidget.ProgressBar = function (self) |
| 378 local print = B.print('ObjectiveWidgets') | |
| 345 local quantity, requiredQuantity = self.info.quantity, self.info.requiredQuantity | 379 local quantity, requiredQuantity = self.info.quantity, self.info.requiredQuantity |
| 346 self.fg:SetPoint('TOPLEFT', self, 'TOPLEFT', 0, 0) | 380 |
| 347 if self.info.finished then | 381 if self.info.finished then |
| 348 self.fg:SetWidth(self.bg:GetWidth() - 2) | 382 self.fg:SetWidth(self.bg:GetWidth() - 2) |
| 349 elseif quantity == 0 then | 383 elseif quantity == 0 then |
| 350 self.fg:Hide() | 384 self.fg:Hide() |
| 351 else | 385 else |
| 352 self.fg:Show() | 386 self.fg:Show() |
| 353 self.fg:SetWidth(self:GetWidth() * (quantity / requiredQuantity)) | 387 self.fg:SetWidth((self:GetWidth()-2) * (quantity / requiredQuantity)) |
| 354 end | 388 end |
| 355 | 389 end |
| 356 end |
