-
Notifications
You must be signed in to change notification settings - Fork 2.3k
Add button to show passive allocation order to passive tree tab (rebranch) #3546
New issue
Have a question about this project? Sign up for a free GitHub account to open an issue and contact its maintainers and the community.
By clicking “Sign up for GitHub”, you agree to our terms of service and privacy statement. We’ll occasionally send you account related emails.
Already on GitHub? Sign in to your account
Changes from all commits
084ada4
f3b42f3
5d83062
9a2f7cb
7152b1d
06ee2ce
File filter
Filter by extension
Conversations
Jump to
Diff view
Diff view
There are no files selected for viewing
| Original file line number | Diff line number | Diff line change | ||
|---|---|---|---|---|
|
|
@@ -58,6 +58,17 @@ local PassiveSpecClass = newClass("PassiveSpec", "UndoHandler", function(self, b | |||
| -- Keys are mastery node IDs, values are mastery effect IDs | ||||
| self.masterySelections = { } | ||||
|
|
||||
| -- List of node allocation order | ||||
| -- Keys are order indexes, values are node IDs | ||||
| self.allocationOrder = { } | ||||
| self.ascendancyAllocationOrder = { } | ||||
|
|
||||
| -- Keys are mastery node IDs, values are mastery effect IDs | ||||
| self.masterySelections = { } | ||||
|
|
||||
| --for postload handler | ||||
| self.initialLoad = true | ||||
|
|
||||
| self:SelectClass(0) | ||||
| end) | ||||
|
|
||||
|
|
@@ -116,6 +127,16 @@ function PassiveSpecClass:Load(xml, dbFileName) | |||
| end | ||||
| end | ||||
| self:ImportFromNodeList(tonumber(xml.attrib.classId), tonumber(xml.attrib.ascendClassId), hashList, masteryEffects) | ||||
| if xml.attrib.allocationOrder then | ||||
| for nodeId in string.gmatch(xml.attrib.allocationOrder, ("%d+")) do | ||||
| table.insert(self.allocationOrder, tonumber(nodeId)) | ||||
| end | ||||
| end | ||||
| if xml.attrib.ascendancyAllocationOrder then | ||||
| for nodeId in string.gmatch(xml.attrib.ascendancyAllocationOrder, ("%d+")) do | ||||
| table.insert(self.ascendancyAllocationOrder, tonumber(nodeId)) | ||||
| end | ||||
| end | ||||
| elseif url then | ||||
| self:DecodeURL(url) | ||||
| end | ||||
|
|
@@ -201,7 +222,9 @@ function PassiveSpecClass:Save(xml) | |||
| classId = tostring(self.curClassId), | ||||
| ascendClassId = tostring(self.curAscendClassId), | ||||
| nodes = table.concat(allocNodeIdList, ","), | ||||
| masteryEffects = table.concat(masterySelections, ",") | ||||
| masteryEffects = table.concat(masterySelections, ","), | ||||
| allocationOrder = table.concat(self.allocationOrder, ","), | ||||
| ascendancyAllocationOrder = table.concat(self.ascendancyAllocationOrder, ",") | ||||
| } | ||||
| t_insert(xml, { | ||||
| -- Legacy format | ||||
|
|
@@ -226,6 +249,9 @@ end | |||
|
|
||||
| function PassiveSpecClass:PostLoad() | ||||
| self:BuildClusterJewelGraphs() | ||||
| self:ReIndexNodeAllocationOrder("allocationOrder") | ||||
| self:ReIndexNodeAllocationOrder("ascendancyAllocationOrder") | ||||
| self.initialLoad = false | ||||
| end | ||||
|
|
||||
| -- Import passive spec from the provided class IDs and node hash list | ||||
|
|
@@ -330,10 +356,10 @@ function PassiveSpecClass:SelectAscendClass(ascendClassId) | |||
| -- Deallocate any allocated ascendancy nodes that don't belong to the new ascendancy class | ||||
| for id, node in pairs(self.allocNodes) do | ||||
| if node.ascendancyName and node.ascendancyName ~= ascendClass.name then | ||||
| node.alloc = false | ||||
| self.allocNodes[id] = nil | ||||
| self:DeallocNode(node) | ||||
| end | ||||
| end | ||||
| self:ReIndexNodeAllocationOrder("ascendancyAllocationOrder") | ||||
|
|
||||
| if ascendClass.startNodeId then | ||||
| -- Allocate the new ascendancy class's start node | ||||
|
|
@@ -376,10 +402,74 @@ function PassiveSpecClass:ResetNodes() | |||
| for id, node in pairs(self.nodes) do | ||||
| if node.type ~= "ClassStart" and node.type ~= "AscendClassStart" then | ||||
| node.alloc = false | ||||
| node.allocationOrder = nil | ||||
| node.ascendancyAllocationOrder = nil | ||||
| self.allocNodes[id] = nil | ||||
| end | ||||
| end | ||||
| wipeTable(self.masterySelections) | ||||
| self.allocationOrder = { } | ||||
| self.ascendancyAllocationOrder = { } | ||||
| end | ||||
|
|
||||
| function PassiveSpecClass:SetAllocationOrder(node) | ||||
| if node.ascendancyName then | ||||
| t_insert(self.ascendancyAllocationOrder, node.id) | ||||
| node.ascendancyAllocationOrder = #self.ascendancyAllocationOrder | ||||
| else | ||||
| t_insert(self.allocationOrder, node.id) | ||||
| node.allocationOrder = #self.allocationOrder | ||||
| end | ||||
| end | ||||
|
|
||||
| function PassiveSpecClass:RemoveFromAllocationOrder(node) | ||||
| if node.ascendancyName then | ||||
| t_remove(self.ascendancyAllocationOrder, node.ascendancyAllocationOrder) | ||||
| node.ascendancyAllocationOrder = nil | ||||
| else | ||||
| t_remove(self.allocationOrder, node.allocationOrder) | ||||
| node.allocationOrder = nil | ||||
| end | ||||
| end | ||||
|
|
||||
| function PassiveSpecClass:ReIndexNodeAllocationOrder(allocationOrder) | ||||
| for i=#self[allocationOrder],1,-1 do | ||||
| nodeId = self[allocationOrder][i] | ||||
| if self.nodes[nodeId] then | ||||
| self.nodes[nodeId][allocationOrder] = i | ||||
| else | ||||
| t_remove(self[allocationOrder], i) | ||||
| end | ||||
| end | ||||
| end | ||||
|
|
||||
| function PassiveSpecClass:SortNodesForRemovingFromAllocationOrder(node) | ||||
| depNodes = node.depends | ||||
| if node.ascendancyName then | ||||
| table.sort(depNodes, function(a, b) | ||||
| if a.ascendancyAllocationOrder == nil and b.ascendancyAllocationOrder == nil then | ||||
| return false | ||||
| elseif a.ascendancyAllocationOrder == nil then | ||||
| return true | ||||
| elseif b.ascendancyAllocationOrder == nil then | ||||
| return false | ||||
| else | ||||
| return a.ascendancyAllocationOrder > b.ascendancyAllocationOrder | ||||
| end | ||||
| end) | ||||
| else | ||||
| table.sort(depNodes, function(a, b) | ||||
| if a.allocationOrder == nil and b.allocationOrder == nil then | ||||
| return false | ||||
| elseif a.allocationOrder == nil then | ||||
| return true | ||||
| elseif b.allocationOrder == nil then | ||||
| return false | ||||
| else | ||||
| return a.allocationOrder > b.allocationOrder | ||||
| end | ||||
| end) | ||||
| end | ||||
| end | ||||
|
|
||||
| -- Allocate the given node, if possible, and all nodes along the path to the node | ||||
|
|
@@ -395,10 +485,14 @@ function PassiveSpecClass:AllocNode(node, altPath) | |||
| if node.dependsOnIntuitiveLeapLike then | ||||
| node.alloc = true | ||||
| self.allocNodes[node.id] = node | ||||
| self:SetAllocationOrder(node) | ||||
| else | ||||
| for _, pathNode in ipairs(altPath or node.path) do | ||||
| local path = altPath or node.path | ||||
| for i = #(path), 1, -1 do | ||||
| local pathNode = path[i] | ||||
| pathNode.alloc = true | ||||
| self.allocNodes[pathNode.id] = pathNode | ||||
| self:SetAllocationOrder(pathNode) | ||||
| end | ||||
| end | ||||
|
|
||||
|
|
@@ -407,8 +501,12 @@ function PassiveSpecClass:AllocNode(node, altPath) | |||
| local parent = node.linked[1] | ||||
| for _, optNode in ipairs(parent.linked) do | ||||
| if optNode.isMultipleChoiceOption and optNode.alloc and optNode ~= node then | ||||
| optNode.alloc = false | ||||
| self.allocNodes[optNode.id] = nil | ||||
| self.DeallocSingleNode(optNode) | ||||
| if optNode.ascendancyName then | ||||
| self:ReIndexNodeAllocationOrder("ascendancyAllocationOrder") | ||||
| else | ||||
| self:ReIndexNodeAllocationOrder("allocationOrder") | ||||
| end | ||||
| end | ||||
| end | ||||
| end | ||||
|
|
@@ -424,14 +522,23 @@ function PassiveSpecClass:DeallocSingleNode(node) | |||
| self:AddMasteryEffectOptionsToNode(node) | ||||
| self.masterySelections[node.id] = nil | ||||
| end | ||||
| if self.allocationOrder[node.allocationOrder] or self.ascendancyAllocationOrder[node.ascendancyAllocationOrder] then | ||||
| self:RemoveFromAllocationOrder(node) | ||||
| end | ||||
| end | ||||
|
|
||||
| -- Deallocate the given node, and all nodes which depend on it (i.e. which are only connected to the tree through this node) | ||||
| function PassiveSpecClass:DeallocNode(node) | ||||
| local effect | ||||
| self:SortNodesForRemovingFromAllocationOrder(node) | ||||
|
|
||||
| for _, depNode in ipairs(node.depends) do | ||||
| self:DeallocSingleNode(depNode) | ||||
| end | ||||
| if node.ascendancyName then | ||||
| self:ReIndexNodeAllocationOrder("ascendancyAllocationOrder") | ||||
| else | ||||
| self:ReIndexNodeAllocationOrder("allocationOrder") | ||||
| end | ||||
|
|
||||
| -- Rebuild all paths and dependencies for all allocated nodes | ||||
| self:BuildAllDependsAndPaths() | ||||
|
|
@@ -774,6 +881,7 @@ function PassiveSpecClass:BuildAllDependsAndPaths() | |||
| if not anyStartFound then | ||||
| -- No start nodes were found through ANY nodes | ||||
| -- Therefore this node and all nodes depending on it are orphans and should be pruned | ||||
| self:SortNodesForRemovingFromAllocationOrder(node) | ||||
| for _, depNode in ipairs(node.depends) do | ||||
| local prune = true | ||||
| for nodeId, itemId in pairs(self.jewels) do | ||||
|
|
@@ -797,9 +905,14 @@ function PassiveSpecClass:BuildAllDependsAndPaths() | |||
| end | ||||
| end | ||||
| if prune then | ||||
| self:DeallocSingleNode(depNode) | ||||
| self:DeallocNode(depNode) | ||||
| end | ||||
| end | ||||
| if node.ascendancyName then | ||||
| self:ReIndexNodeAllocationOrder("ascendancyAllocationOrder") | ||||
| else | ||||
| self:ReIndexNodeAllocationOrder("allocationOrder") | ||||
| end | ||||
| end | ||||
| end | ||||
|
|
||||
|
|
@@ -853,9 +966,27 @@ end | |||
|
|
||||
| function PassiveSpecClass:BuildClusterJewelGraphs() | ||||
| -- Remove old subgraphs | ||||
| local reserverdAllocationOrders = {} | ||||
| for id, subGraph in pairs(self.subGraphs) do | ||||
| table.sort(subGraph.nodes, function(a, b) | ||||
| if a.allocationOrder == nil and b.allocationOrder == nil then | ||||
| return false | ||||
| elseif a.allocationOrder == nil then | ||||
| return true | ||||
| elseif b.allocationOrder == nil then | ||||
| return false | ||||
| else | ||||
| return a.allocationOrder > b.allocationOrder | ||||
| end | ||||
| end) | ||||
| for _, node in ipairs(subGraph.nodes) do | ||||
| if node.id then | ||||
| if node.alloc then | ||||
| if node.allocationOrder ~= nil then | ||||
| reserverdAllocationOrders[node.id] = node.allocationOrder | ||||
| node.allocationOrder = nil | ||||
| end | ||||
| end | ||||
| self.nodes[node.id] = nil | ||||
| if self.allocNodes[node.id] then | ||||
| -- Reserve the allocation in case the node is regenerated | ||||
|
|
@@ -893,17 +1024,36 @@ function PassiveSpecClass:BuildClusterJewelGraphs() | |||
| end | ||||
| end | ||||
|
|
||||
| ConPrintTable(reserverdAllocationOrders) | ||||
|
Member
There was a problem hiding this comment. Choose a reason for hiding this commentThe reason will be displayed to describe this comment to others. Learn more.
Suggested change
|
||||
| -- (Re-)allocate subgraph nodes | ||||
| for _, nodeId in ipairs(self.allocSubgraphNodes) do | ||||
| local sortedAllocSubgraphNodes = {} | ||||
| for i=#self.allocSubgraphNodes, 1, -1 do | ||||
| sortedAllocSubgraphNodes[#sortedAllocSubgraphNodes+1] = self.allocSubgraphNodes[i] | ||||
| end | ||||
| for _, nodeId in ipairs(sortedAllocSubgraphNodes) do | ||||
| local node = self.nodes[nodeId] | ||||
| if node then | ||||
| node.alloc = true | ||||
| if not self.allocNodes[nodeId] then | ||||
| self.allocNodes[nodeId] = node | ||||
| t_insert(self.allocExtendedNodes, nodeId) | ||||
| end | ||||
| if not self.initialLoad then | ||||
| if reserverdAllocationOrders[nodeId] then | ||||
| self.allocationOrder[reserverdAllocationOrders[nodeId]] = nodeId | ||||
| node.allocationOrder = reserverdAllocationOrders[nodeId] | ||||
| reserverdAllocationOrders[nodeId] = nil | ||||
| else | ||||
| self:SetAllocationOrder(node) | ||||
| end | ||||
| end | ||||
| end | ||||
| end | ||||
| for nodeId, unallocated in pairs(reserverdAllocationOrders) do | ||||
| self:RemoveFromAllocationOrder(self.nodes[nodeId]) | ||||
| end | ||||
| ConPrintTable(self.allocationOrder) | ||||
|
Member
There was a problem hiding this comment. Choose a reason for hiding this commentThe reason will be displayed to describe this comment to others. Learn more.
Suggested change
|
||||
| self:ReIndexNodeAllocationOrder("allocationOrder") | ||||
| wipeTable(self.allocSubgraphNodes) | ||||
|
|
||||
| -- Rebuild paths to account for new/removed nodes | ||||
|
|
@@ -1319,16 +1469,24 @@ function PassiveSpecClass:CreateUndoState() | |||
| for mastery, effect in pairs(self.masterySelections) do | ||||
| selections[mastery] = effect | ||||
| end | ||||
| local allocationOrder = copyTable(self.allocationOrder) | ||||
| local ascendancyAllocationOrder = copyTable(self.ascendancyAllocationOrder) | ||||
| return { | ||||
| classId = self.curClassId, | ||||
| ascendClassId = self.curAscendClassId, | ||||
| hashList = allocNodeIdList, | ||||
| masteryEffects = selections | ||||
| masteryEffects = selections, | ||||
| allocationOrder = allocationOrder, | ||||
| ascendancyAllocationOrder = ascendancyAllocationOrder | ||||
| } | ||||
| end | ||||
|
|
||||
| function PassiveSpecClass:RestoreUndoState(state) | ||||
| self:ImportFromNodeList(state.classId, state.ascendClassId, state.hashList, state.masteryEffects) | ||||
| self.allocationOrder = state.allocationOrder | ||||
| self.ascendancyAllocationOrder = state.ascendancyAllocationOrder | ||||
| self:ReIndexNodeAllocationOrder("allocationOrder") | ||||
| self:ReIndexNodeAllocationOrder("ascendancyAllocationOrder") | ||||
| self:SetWindowTitleWithBuildClass() | ||||
| end | ||||
|
|
||||
|
|
||||
| Original file line number | Diff line number | Diff line change | ||||
|---|---|---|---|---|---|---|
|
|
@@ -75,6 +75,9 @@ function PassiveTreeViewClass:Load(xml, fileName) | |||||
| if xml.attrib.searchStr then | ||||||
| self.searchStr = xml.attrib.searchStr | ||||||
| end | ||||||
| if xml.attrib.showAllocationOrder then | ||||||
| self.showAllocationOrder = xml.attrib.showAllocationOrder == "true" | ||||||
| end | ||||||
| if xml.attrib.showHeatMap then | ||||||
| self.showHeatMap = xml.attrib.showHeatMap == "true" | ||||||
| end | ||||||
|
|
@@ -89,6 +92,7 @@ function PassiveTreeViewClass:Save(xml) | |||||
| zoomX = tostring(self.zoomX), | ||||||
| zoomY = tostring(self.zoomY), | ||||||
| searchStr = self.searchStr, | ||||||
| showAllocationOrder = tostring(self.showAllocationOrder), | ||||||
| showHeatMap = tostring(self.showHeatMap), | ||||||
| showStatDifferences = tostring(self.showStatDifferences), | ||||||
| } | ||||||
|
|
@@ -670,6 +674,20 @@ function PassiveTreeViewClass:Draw(build, viewPort, inputEvents) | |||||
| local size = 175 * scale / self.zoom ^ 0.4 | ||||||
| DrawImage(self.highlightRing, scrX - size, scrY - size, size * 2, size * 2) | ||||||
| end | ||||||
| if self.showAllocationOrder and node.allocationOrder ~= nil then | ||||||
|
Member
There was a problem hiding this comment. Choose a reason for hiding this commentThe reason will be displayed to describe this comment to others. Learn more.
Suggested change
|
||||||
| SetDrawLayer(nile, 29) | ||||||
| SetDrawColor(1, 0, 0) | ||||||
| local size = 100 * scale | ||||||
| local offset = node.size * 1.8 * scale | ||||||
| DrawString(m_floor(scrX - offset), m_floor(scrY - offset), "LEFT", size, "VAR", tostring(node.allocationOrder)) | ||||||
| end | ||||||
| if self.showAllocationOrder and node.ascendancyAllocationOrder ~= nil then | ||||||
| SetDrawLayer(nile, 29) | ||||||
| SetDrawColor(1, 0, 0) | ||||||
| local size = 100 * scale | ||||||
| local offset = node.size * 1.8 * scale | ||||||
| DrawString(m_floor(scrX - offset), m_floor(scrY - offset), "LEFT", size, "VAR", tostring(node.ascendancyAllocationOrder)) | ||||||
| end | ||||||
|
Comment on lines
+678
to
+690
Member
There was a problem hiding this comment. Choose a reason for hiding this commentThe reason will be displayed to describe this comment to others. Learn more. This can all be combined into two calls to a local function |
||||||
| if node == hoverNode and (node.type ~= "Socket" or not IsKeyDown("SHIFT")) and (node.type ~= "Mastery" or node.masteryEffects) and not IsKeyDown("CTRL") and not main.popups[1] then | ||||||
| -- Draw tooltip | ||||||
| SetDrawLayer(nil, 100) | ||||||
|
|
||||||
| Original file line number | Diff line number | Diff line change | ||
|---|---|---|---|---|
|
|
@@ -107,8 +107,11 @@ local TreeTabClass = newClass("TreeTab", "ControlHost", function(self, build) | |||
| self.controls.treeSearch = new("EditControl", {"LEFT",self.controls.export,"RIGHT"}, 8, 0, main.portraitMode and 200 or 300, 20, "", "Search", "%c%(%)", 100, function(buf) | ||||
| self.viewer.searchStr = buf | ||||
| end) | ||||
| self.controls.treeSearch.tooltipText = "Uses Lua pattern matching for complex searches" | ||||
| self.controls.treeHeatMap = new("CheckBoxControl", {"LEFT",self.controls.treeSearch,"RIGHT"}, 130, 0, 20, "Show Node Power:", function(state) | ||||
| self.controls.treeSearch.tooltipText = "Uses Lua pattern matching for complex searches" | ||||
| self.controls.treeAllocationOrder = new("CheckBoxControl", {"LEFT",self.controls.treeSearch,"RIGHT"}, 194, 0, 20, "Show Node Allocation Order:", function(state) | ||||
| self.viewer.showAllocationOrder = state | ||||
| end) | ||||
| self.controls.treeHeatMap = new("CheckBoxControl", {"LEFT",self.controls.treeAllocationOrder,"RIGHT"}, 130, 0, 20, "Show Node Power:", function(state) | ||||
| self.viewer.showHeatMap = state | ||||
| self.controls.treeHeatMapStatSelect.shown = state | ||||
| end) | ||||
|
|
@@ -228,6 +231,8 @@ function TreeTabClass:Draw(viewPort, inputEvents) | |||
| self.controls.treeSearch:SetText(self.viewer.searchStr) | ||||
| end | ||||
|
|
||||
| self.controls.treeAllocationOrder.state = self.viewer.showAllocationOrder | ||||
|
|
||||
|
Member
There was a problem hiding this comment. Choose a reason for hiding this commentThe reason will be displayed to describe this comment to others. Learn more.
Suggested change
|
||||
| self.controls.treeHeatMap.state = self.viewer.showHeatMap | ||||
| self.controls.treeHeatMapStatSelect.list = self.powerStatList | ||||
| self.controls.treeHeatMapStatSelect.selIndex = 1 | ||||
|
|
||||
There was a problem hiding this comment.
Choose a reason for hiding this comment
The reason will be displayed to describe this comment to others. Learn more.
This logic can be simplified: