Skip to content
Merged
Show file tree
Hide file tree
Changes from all commits
Commits
File filter

Filter by extension

Filter by extension

Conversations
Failed to load comments.
Loading
Jump to
Jump to file
Failed to load files.
Loading
Diff view
Diff view
115 changes: 115 additions & 0 deletions spec/System/TestClusterJewelGraphs_spec.lua
Original file line number Diff line number Diff line change
@@ -0,0 +1,115 @@
describe("Cluster jewel subgraphs", function()
local function countSubgraphs(spec)
local count = 0
for _ in pairs(spec.subGraphs) do
count = count + 1
end
return count
end

local function getOuterSocket(spec)
for nodeId in pairs(spec.tree.sockets) do
local node = spec.nodes[nodeId]
if node and node.expansionJewel and node.expansionJewel.size == 2 then
return node
end
end
end

local function addItem(raw)
local item = new("Item"):Item(raw)
build.itemsTab:AddItem(item, true)
return item
end

local function addKeystoneCluster()
return addItem([[Rarity: UNIQUE
One With Nothing
Small Cluster Jewel
Implicits: 0
Adds Hollow Palm Technique]])
end

before_each(function()
newBuild()
end)

it("updates the graph when an outer socket allocation changes", function()
local spec = build.spec
local socket = getOuterSocket(spec)
local jewel = addKeystoneCluster()
spec.jewels[socket.id] = jewel.id
spec.extended_hashes = { 123 }
spec.jewel_data = {
[socket.id] = {
subgraph = {
groups = {
keystone = { proxy = socket.expansionJewel.proxy, nodes = { "123" } },
},
nodes = {
["123"] = { group = "keystone", isKeystone = true, orbitIndex = 0 },
},
},
},
}

spec:BuildClusterJewelGraphs()
assert.are.equal(0, countSubgraphs(spec))

spec:AllocNode(socket)
assert.are.equal(1, countSubgraphs(spec))
local _, subgraph = next(spec.subGraphs)
assert.is_true(subgraph.nodes[1].alloc)

spec:DeallocNode(socket)
assert.are.equal(0, countSubgraphs(spec))
end)

it("only builds nested graphs for allocated cluster sockets", function()
local spec = build.spec
local outerSocket = getOuterSocket(spec)
spec:AllocNode(outerSocket)

local largeCluster = addItem([[Rarity: RARE
New Item
Large Cluster Jewel
Cluster Jewel Skill: affliction_chaos_damage
Cluster Jewel Node Count: 8
Implicits: 3
Adds 8 Passive Skills
2 Added Passive Skills are Jewel Sockets
Added Small Passive Skills grant: 12% increased Chaos Damage]])
spec.jewels[outerSocket.id] = largeCluster.id
spec:BuildClusterJewelGraphs()

local nestedSocket
for _, subgraph in pairs(spec.subGraphs) do
for _, node in ipairs(subgraph.nodes) do
if node.type == "Socket" then
nestedSocket = node
break
end
end
if nestedSocket then
break
end
end
assert.is_truthy(nestedSocket)

local nestedJewel = addKeystoneCluster()
spec.jewels[nestedSocket.id] = nestedJewel.id
spec:BuildClusterJewelGraphs()
assert.are.equal(1, countSubgraphs(spec))

nestedSocket = spec.nodes[nestedSocket.id]
spec:AllocNode(nestedSocket)
assert.are.equal(2, countSubgraphs(spec))

spec:BuildClusterJewelGraphs()
assert.are.equal(2, countSubgraphs(spec))

nestedSocket = spec.nodes[nestedSocket.id]
spec:DeallocNode(nestedSocket)
assert.are.equal(1, countSubgraphs(spec))
end)
end)
30 changes: 23 additions & 7 deletions src/Classes/PassiveSpec.lua
Original file line number Diff line number Diff line change
Expand Up @@ -778,11 +778,14 @@ function PassiveSpecClass:AllocNode(node, altPath)
end

-- Allocate all nodes along the path
local rebuildClusterJewelGraphs = false
if #node.intuitiveLeapLikesAffecting > 0 then
rebuildClusterJewelGraphs = not node.alloc and node.expansionJewel ~= nil
node.alloc = true
self.allocNodes[node.id] = node
else
for _, pathNode in ipairs(altPath or node.path) do
rebuildClusterJewelGraphs = rebuildClusterJewelGraphs or not pathNode.alloc and pathNode.expansionJewel ~= nil
pathNode.alloc = true
self.allocNodes[pathNode.id] = pathNode
end
Expand All @@ -799,8 +802,12 @@ function PassiveSpecClass:AllocNode(node, altPath)
end
end

-- Rebuild all dependencies and paths for all allocated nodes
self:BuildAllDependsAndPaths()
if rebuildClusterJewelGraphs then
self:BuildClusterJewelGraphs()
else
-- Rebuild all dependencies and paths for all allocated nodes
self:BuildAllDependsAndPaths()
end
end

function PassiveSpecClass:DeallocSingleNode(node)
Expand All @@ -814,12 +821,18 @@ 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 rebuildClusterJewelGraphs = false
for _, depNode in ipairs(node.depends) do
rebuildClusterJewelGraphs = rebuildClusterJewelGraphs or depNode.alloc and depNode.expansionJewel ~= nil
self:DeallocSingleNode(depNode)
end

-- Rebuild all paths and dependencies for all allocated nodes
self:BuildAllDependsAndPaths()
if rebuildClusterJewelGraphs then
self:BuildClusterJewelGraphs()
else
-- Rebuild all paths and dependencies for all allocated nodes
self:BuildAllDependsAndPaths()
end
end

-- Count the number of allocated nodes and allocated ascendancy nodes
Expand Down Expand Up @@ -1765,7 +1778,7 @@ function PassiveSpecClass:BuildClusterJewelGraphs()
for nodeId in pairs(self.tree.sockets) do
local node = self.tree.nodes[nodeId]
local jewel = self:GetSocketedJewel(nodeId)
if node and node.expansionJewel and node.expansionJewel.size == 2 and jewel and jewel.jewelData.clusterJewelValid then
if node and self.allocNodes[node.id] and node.expansionJewel and node.expansionJewel.size == 2 and jewel and jewel.jewelData.clusterJewelValid then
-- This is a Large Jewel Socket, and it has a cluster jewel in it
self:BuildSubgraph(jewel, self.nodes[nodeId], nil, nil, importedNodes, importedGroups)
end
Expand Down Expand Up @@ -1971,7 +1984,9 @@ function PassiveSpecClass:BuildSubgraph(jewel, parentSocket, id, upSize, importe
if proxyGroup then
for id, data in pairs(importedNodes) do
if proxyGroup == data.group then
if node.oidx == data.orbitIndex and not data.isMastery then
local matches = node.type == "Keystone" and data.isKeystone
or (node.oidx == data.orbitIndex and not data.isMastery)
if matches then
for _, extendedId in ipairs(importedGroups[proxyGroup].nodes) do
if id == extendedId and inExtendedHashes(tonumber(id)) then
return true
Expand Down Expand Up @@ -2265,7 +2280,8 @@ function PassiveSpecClass:BuildSubgraph(jewel, parentSocket, id, upSize, importe
if node.type == "Socket" then
-- Recurse to smaller jewels
local jewel = self:GetSocketedJewel(node.id)
if jewel and jewel.jewelData.clusterJewelValid then
-- Allocated subgraph nodes are temporarily preserved outside allocNodes while rebuilding.
if (self.allocNodes[node.id] or isValueInArray(self.allocSubgraphNodes, node.id)) and jewel and jewel.jewelData.clusterJewelValid then
self:BuildSubgraph(jewel, node, id, upSize, importedNodes, importedGroups)
end
end
Expand Down
Loading