improved custom card support
This commit is contained in:
parent
6600610076
commit
c785baa4be
@ -64,51 +64,22 @@ end
|
|||||||
-- and creating the keyed lookup tables for the cards. This is a coroutine which will
|
-- and creating the keyed lookup tables for the cards. This is a coroutine which will
|
||||||
-- spread the workload by processing 20 cards before yielding.
|
-- spread the workload by processing 20 cards before yielding.
|
||||||
function buildIndex()
|
function buildIndex()
|
||||||
local cardCount = 0
|
cardCount = 0
|
||||||
indexingDone = false
|
indexingDone = false
|
||||||
otherCardsDetected = false
|
otherCardsDetected = false
|
||||||
|
|
||||||
-- process the allcardsbag itself
|
-- process the allcardsbag itself
|
||||||
for _, cardData in ipairs(self.getData().ContainedObjects) do
|
local selfData = self.getData()
|
||||||
addCardToIndex(cardData)
|
if selfData.ContainedObjects then
|
||||||
cardCount = cardCount + 1
|
processContainedObjects(selfData.ContainedObjects)
|
||||||
if cardCount > 19 then
|
|
||||||
cardCount = 0
|
|
||||||
coroutine.yield(0)
|
|
||||||
end
|
|
||||||
end
|
end
|
||||||
|
|
||||||
-- process hotfix bags (and the additional playercards bag)
|
-- process hotfix bags (and the additional playercards bag)
|
||||||
for _, hotfixBag in ipairs(getObjectsWithTag("AllCardsHotfix")) do
|
for _, hotfixBag in ipairs(getObjectsWithTag("AllCardsHotfix")) do
|
||||||
local hotfixData = hotfixBag.getData()
|
local hotfixData = hotfixBag.getData()
|
||||||
|
if hotfixData.ContainedObjects then
|
||||||
-- if the bag is empty, continue with the next bag
|
processContainedObjects(hotfixData.ContainedObjects, hotfixData.CustomDeck)
|
||||||
if not hotfixData.ContainedObjects then
|
|
||||||
goto nextBag
|
|
||||||
end
|
end
|
||||||
|
|
||||||
for _, cardData in ipairs(hotfixData.ContainedObjects) do
|
|
||||||
if cardData.ContainedObjects then
|
|
||||||
-- process containers
|
|
||||||
for _, deepCardData in ipairs(cardData.ContainedObjects) do
|
|
||||||
addCardToIndex(deepCardData)
|
|
||||||
cardCount = cardCount + 1
|
|
||||||
if cardCount > 19 then
|
|
||||||
cardCount = 0
|
|
||||||
coroutine.yield(0)
|
|
||||||
end
|
|
||||||
end
|
|
||||||
else
|
|
||||||
-- process single cards
|
|
||||||
addCardToIndex(cardData)
|
|
||||||
cardCount = cardCount + 1
|
|
||||||
if cardCount > 19 then
|
|
||||||
cardCount = 0
|
|
||||||
coroutine.yield(0)
|
|
||||||
end
|
|
||||||
end
|
|
||||||
end
|
|
||||||
::nextBag::
|
|
||||||
end
|
end
|
||||||
|
|
||||||
buildSupplementalIndexes()
|
buildSupplementalIndexes()
|
||||||
@ -117,6 +88,43 @@ function buildIndex()
|
|||||||
return 1
|
return 1
|
||||||
end
|
end
|
||||||
|
|
||||||
|
-- Processes the contained objects for cards to add to the index
|
||||||
|
function processContainedObjects(containedObjects, customDeck)
|
||||||
|
for _, objData in ipairs(containedObjects) do
|
||||||
|
if objData.ContainedObjects then
|
||||||
|
-- recursively process nested containers
|
||||||
|
processContainedObjects(objData.ContainedObjects, objData.CustomDeck)
|
||||||
|
else
|
||||||
|
-- we might need to fix the "CustomDeck" entry for cards inside decks since TTS doesn't update it while they are in bags
|
||||||
|
if customDeck then
|
||||||
|
local wantedCustomDeckIdStr = tostring(objData.CardID):sub(1, -3)
|
||||||
|
local presentCustomDeckIdNum = next(objData.CustomDeck)
|
||||||
|
|
||||||
|
-- type conversion (TTS seems to store these as strings, but reads them as numbers)
|
||||||
|
local wantedCustomDeckIdNum = tonumber(wantedCustomDeckIdStr)
|
||||||
|
|
||||||
|
if wantedCustomDeckIdNum ~= presentCustomDeckIdNum then
|
||||||
|
if customDeck[wantedCustomDeckIdNum] then
|
||||||
|
objData.CustomDeck = {}
|
||||||
|
objData.CustomDeck[wantedCustomDeckIdStr] = customDeck[wantedCustomDeckIdNum]
|
||||||
|
log("Correct CustomDeckData for " .. objData.Nickname)
|
||||||
|
else
|
||||||
|
log("Could not correct CustomDeckData for " .. objData.Nickname)
|
||||||
|
return
|
||||||
|
end
|
||||||
|
end
|
||||||
|
end
|
||||||
|
|
||||||
|
addCardToIndex(objData)
|
||||||
|
cardCount = cardCount + 1
|
||||||
|
if cardCount > 19 then
|
||||||
|
cardCount = 0
|
||||||
|
coroutine.yield(0)
|
||||||
|
end
|
||||||
|
end
|
||||||
|
end
|
||||||
|
end
|
||||||
|
|
||||||
-- Adds a card to any indexes it should be a part of, based on its metadata
|
-- Adds a card to any indexes it should be a part of, based on its metadata
|
||||||
---@param cardData table TTS object data for the card
|
---@param cardData table TTS object data for the card
|
||||||
function addCardToIndex(cardData)
|
function addCardToIndex(cardData)
|
||||||
@ -178,6 +186,17 @@ function buildSupplementalIndexes()
|
|||||||
|
|
||||||
-- add to cycle index
|
-- add to cycle index
|
||||||
local cycleName = card.metadata.cycle
|
local cycleName = card.metadata.cycle
|
||||||
|
|
||||||
|
-- if this is a minicard without cycle, check the parent card for cycle data
|
||||||
|
if not cycleName and card.metadata.type == "Minicard" then
|
||||||
|
-- TO-DO: use a more robust detection instead of 5 characters
|
||||||
|
local parentId = string.match(card.metadata.id, ".....")
|
||||||
|
local parent = cardIdIndex[parentId]
|
||||||
|
if parent and parent.metadata.cycle then
|
||||||
|
cycleName = parent.metadata.cycle
|
||||||
|
end
|
||||||
|
end
|
||||||
|
|
||||||
if cycleName then
|
if cycleName then
|
||||||
cycleName = string.lower(cycleName)
|
cycleName = string.lower(cycleName)
|
||||||
|
|
||||||
@ -189,18 +208,14 @@ function buildSupplementalIndexes()
|
|||||||
else
|
else
|
||||||
-- track cards without defined cycle (should only be fan-made cards)
|
-- track cards without defined cycle (should only be fan-made cards)
|
||||||
cycleName = "other"
|
cycleName = "other"
|
||||||
log(card.metadata.id)
|
|
||||||
otherCardsDetected = true
|
otherCardsDetected = true
|
||||||
end
|
end
|
||||||
|
|
||||||
-- only add official cards with level to cycle index, but all fan-made cards
|
-- maybe initialize table
|
||||||
if card.metadata.level or cycleName == "other" then
|
if cycleIndex[cycleName] == nil then
|
||||||
-- maybe initialize table
|
cycleIndex[cycleName] = {}
|
||||||
if cycleIndex[cycleName] == nil then
|
|
||||||
cycleIndex[cycleName] = {}
|
|
||||||
end
|
|
||||||
table.insert(cycleIndex[cycleName], card.metadata.id)
|
|
||||||
end
|
end
|
||||||
|
table.insert(cycleIndex[cycleName], card.metadata.id)
|
||||||
end
|
end
|
||||||
end
|
end
|
||||||
|
|
||||||
@ -278,8 +293,9 @@ end
|
|||||||
|
|
||||||
-- Returns a list of cards from the bag matching a cycle
|
-- Returns a list of cards from the bag matching a cycle
|
||||||
---@param params table
|
---@param params table
|
||||||
-- cycle: String cycle to retrieve ("The Scarlet Keys" etc.)
|
-- cycle: string Name of the cycle to retrieve ("The Scarlet Keys" etc.)
|
||||||
-- sortByMetadata: true to sort the table by metadata instead of ID
|
-- sortByMetadata: boolean If true, sorts the table by metadata instead of ID
|
||||||
|
-- includeNoLevelCards: boolean If true, includes cards without level
|
||||||
---@return table: If the indexes are still being constructed, returns an empty table.
|
---@return table: If the indexes are still being constructed, returns an empty table.
|
||||||
-- Otherwise, a list of tables, each with the following fields
|
-- Otherwise, a list of tables, each with the following fields
|
||||||
-- data: TTS object data, suitable for spawning the card
|
-- data: TTS object data, suitable for spawning the card
|
||||||
@ -288,17 +304,18 @@ function getCardsByCycle(params)
|
|||||||
if not isIndexReady() then return {} end
|
if not isIndexReady() then return {} end
|
||||||
|
|
||||||
local cycleData = cycleIndex[string.lower(params.cycle)] or {}
|
local cycleData = cycleIndex[string.lower(params.cycle)] or {}
|
||||||
if not params.sortByMetadata then
|
|
||||||
return cycleData
|
-- create a copy of the data to not change the source
|
||||||
|
local cardList = {}
|
||||||
|
for _, id in ipairs(cycleData) do
|
||||||
|
-- only include cards without level if requested
|
||||||
|
if cardIdIndex[id].metadata.level or params.includeNoLevelCards then
|
||||||
|
table.insert(cardList, id)
|
||||||
|
end
|
||||||
end
|
end
|
||||||
|
|
||||||
-- sort list by metadata (useful for custom cards without proper IDs)
|
-- sort list by metadata (useful for custom cards without proper IDs)
|
||||||
local cardList = {}
|
if params.sortByMetadata and #cardList > 0 then
|
||||||
for _, id in ipairs(cycleData) do
|
|
||||||
table.insert(cardList, id)
|
|
||||||
end
|
|
||||||
|
|
||||||
if #cardList > 0 then
|
|
||||||
table.sort(cardList, metadataSortFunction)
|
table.sort(cardList, metadataSortFunction)
|
||||||
end
|
end
|
||||||
return cardList
|
return cardList
|
||||||
@ -340,13 +357,15 @@ end
|
|||||||
|
|
||||||
-- helper function to calculate the class value for sorting from the "|" separated string
|
-- helper function to calculate the class value for sorting from the "|" separated string
|
||||||
function getClassValueFromString(s)
|
function getClassValueFromString(s)
|
||||||
|
s = s or "NoClass"
|
||||||
local classValueList = {
|
local classValueList = {
|
||||||
Guardian = 1,
|
Guardian = 1,
|
||||||
Seeker = 2,
|
Seeker = 2,
|
||||||
Rogue = 3,
|
Rogue = 3,
|
||||||
Mystic = 4,
|
Mystic = 4,
|
||||||
Survivor = 5,
|
Survivor = 5,
|
||||||
Neutral = 6
|
Neutral = 6,
|
||||||
|
NoClass = 7
|
||||||
}
|
}
|
||||||
local classValue = 0
|
local classValue = 0
|
||||||
for str in s:gmatch("([^|]+)") do
|
for str in s:gmatch("([^|]+)") do
|
||||||
|
@ -77,12 +77,17 @@ do
|
|||||||
-- Returns a list of cards from the bag matching a cycle
|
-- Returns a list of cards from the bag matching a cycle
|
||||||
---@param cycle string Cycle to retrieve ("The Scarlet Keys" etc.)
|
---@param cycle string Cycle to retrieve ("The Scarlet Keys" etc.)
|
||||||
---@param sortByMetadata boolean If true, sorts the table by metadata instead of ID
|
---@param sortByMetadata boolean If true, sorts the table by metadata instead of ID
|
||||||
|
---@param includeNoLevelCards boolean If true, includes cards without level
|
||||||
---@return table: If the indexes are still being constructed, returns an empty table.
|
---@return table: If the indexes are still being constructed, returns an empty table.
|
||||||
-- Otherwise, a list of tables, each with the following fields
|
-- Otherwise, a list of tables, each with the following fields
|
||||||
-- data: TTS object data, suitable for spawning the card
|
-- data: TTS object data, suitable for spawning the card
|
||||||
-- metadata: Table of parsed metadata
|
-- metadata: Table of parsed metadata
|
||||||
AllCardsBagApi.getCardsByCycle = function(cycle, sortByMetadata)
|
AllCardsBagApi.getCardsByCycle = function(cycle, sortByMetadata, includeNoLevelCards)
|
||||||
return returnCopyOfList(getAllCardsBag().call("getCardsByCycle", { cycle = cycle, sortByMetadata = sortByMetadata }))
|
return returnCopyOfList(getAllCardsBag().call("getCardsByCycle", {
|
||||||
|
cycle = cycle,
|
||||||
|
sortByMetadata = sortByMetadata,
|
||||||
|
includeNoLevelCards = includeNoLevelCards
|
||||||
|
}))
|
||||||
end
|
end
|
||||||
|
|
||||||
-- Constructs a list of available basic weaknesses by starting with the full pool of basic
|
-- Constructs a list of available basic weaknesses by starting with the full pool of basic
|
||||||
|
@ -493,7 +493,9 @@ end
|
|||||||
---@param groupName string Name of the group to spawn, matching a key in InvestigatorPanelData
|
---@param groupName string Name of the group to spawn, matching a key in InvestigatorPanelData
|
||||||
function spawnInvestigators(groupName)
|
function spawnInvestigators(groupName)
|
||||||
if INVESTIGATOR_GROUPS[groupName] == nil then
|
if INVESTIGATOR_GROUPS[groupName] == nil then
|
||||||
printToAll("No investigator data for " .. groupName .. " yet")
|
if groupName ~= "Other" then
|
||||||
|
printToAll("No investigator data for '" .. groupName .. "' yet")
|
||||||
|
end
|
||||||
return
|
return
|
||||||
end
|
end
|
||||||
|
|
||||||
@ -693,15 +695,17 @@ function spawnCycle(cycle)
|
|||||||
prepareToPlaceCards()
|
prepareToPlaceCards()
|
||||||
spawnInvestigators(cycle)
|
spawnInvestigators(cycle)
|
||||||
|
|
||||||
-- sort custom cards
|
-- sort custom cards and include cards without level
|
||||||
local sortByMetadata = false
|
local sortByMetadata = false
|
||||||
|
local includeNoLevelCards = false
|
||||||
if cycle == "Other" then
|
if cycle == "Other" then
|
||||||
sortByMetadata = true
|
sortByMetadata = true
|
||||||
|
includeNoLevelCards = true
|
||||||
end
|
end
|
||||||
|
|
||||||
spawnBag.spawn({
|
spawnBag.spawn({
|
||||||
name = "cycle" .. cycle,
|
name = "cycle" .. cycle,
|
||||||
cards = allCardsBagApi.getCardsByCycle(cycle, sortByMetadata),
|
cards = allCardsBagApi.getCardsByCycle(cycle, sortByMetadata, includeNoLevelCards),
|
||||||
globalPos = self.positionToWorld(startPositions.cycle),
|
globalPos = self.positionToWorld(startPositions.cycle),
|
||||||
rotation = FACE_UP_ROTATION,
|
rotation = FACE_UP_ROTATION,
|
||||||
spread = true,
|
spread = true,
|
||||||
|
Loading…
Reference in New Issue
Block a user