diff --git a/config.json b/config.json index 90df3503..2c6d51e1 100644 --- a/config.json +++ b/config.json @@ -3,6 +3,7 @@ "ComponentTags_path": "ComponentTags.json", "CustomUIAssets_path": "CustomUIAssets.json", "DecalPallet_path": "DecalPallet.json", + "Decals": [], "GameComplexity": "", "GameMode": "Arkham Horror LCG - Super Complete Edition", "GameType": "", @@ -140,7 +141,7 @@ "ArkhamDBDeckImporter.a28140", "Configuration.03804b", "DrawingTool.280086", - "PlaymatImageSwapper.b7b45b", + "PlayAreaImageSwapper.b7b45b", "AllPlayerCards.15bb07", "InvestigatorSkillTracker.af7ed7", "InvestigatorSkillTracker.e598c2", diff --git a/objects/ChaosBagStatTracker.766620.json b/objects/ChaosBagStatTracker.766620.json index 4a279b19..4bf04015 100644 --- a/objects/ChaosBagStatTracker.766620.json +++ b/objects/ChaosBagStatTracker.766620.json @@ -22,7 +22,7 @@ "ImageURL": "https://i.imgur.com/SBE8GR5.png", "WidthScale": 0 }, - "Description": "Only tracks tokens that actually hit the playmat.\n\nAll credit goes to TadGH!", + "Description": "", "DragSelectable": true, "GMNotes": "", "GUID": "766620", diff --git a/objects/FlexTableControl.bd69bd.ttslua b/objects/FlexTableControl.bd69bd.ttslua index 090285a0..4991a9ca 100644 --- a/objects/FlexTableControl.bd69bd.ttslua +++ b/objects/FlexTableControl.bd69bd.ttslua @@ -1,188 +1,172 @@ -tableHeightOffset =-9 +tableHeightOffset = -9 + function onSave() - saved_data = JSON.encode({tid=tableImageData, cd=checkData}) - --saved_data = "" - return saved_data + return JSON.encode({ tid = tableImageData, cd = checkData }) end function onload(saved_data) - --Loads the tracking for if the game has started yet - if saved_data ~= "" then - local loaded_data = JSON.decode(saved_data) - tableImageData = loaded_data.tid - checkData = loaded_data.cd - else - tableImageData = {} - checkData = {move=false, scale=false} - end + if saved_data ~= "" then + local loaded_data = JSON.decode(saved_data) + tableImageData = loaded_data.tid + checkData = loaded_data.cd + else + tableImageData = {} + checkData = { move = false, scale = false } + end - --Disables interactable status of objects with GUID in list - for _, guid in ipairs(ref_noninteractable) do - local obj = getObjectFromGUID(guid) - if obj then obj.interactable = false end - end + --Disables interactable status of objects with GUID in list + for _, guid in ipairs(ref_noninteractable) do + local obj = getObjectFromGUID(guid) + if obj then obj.interactable = false end + end - --Establish references to table parts - obj_leg1 = getObjectFromGUID("afc863") - obj_leg2 = getObjectFromGUID("c8edca") - obj_leg3 = getObjectFromGUID("393bf7") - obj_leg4 = getObjectFromGUID("12c65e") - obj_surface = getObjectFromGUID("4ee1f2") - obj_side_top = getObjectFromGUID("35b95f") - obj_side_bot = getObjectFromGUID("f938a2") - obj_side_lef = getObjectFromGUID("9f95fd") - obj_side_rig = getObjectFromGUID("5af8f2") + --Establish references to table parts + obj_leg1 = getObjectFromGUID("afc863") + obj_leg2 = getObjectFromGUID("c8edca") + obj_leg3 = getObjectFromGUID("393bf7") + obj_leg4 = getObjectFromGUID("12c65e") + obj_surface = getObjectFromGUID("4ee1f2") + obj_side_top = getObjectFromGUID("35b95f") + obj_side_bot = getObjectFromGUID("f938a2") + obj_side_lef = getObjectFromGUID("9f95fd") + obj_side_rig = getObjectFromGUID("5af8f2") - controlActive = true - createOpenCloseButton() + controlActive = true + createOpenCloseButton() end - - --Activation/deactivation of control panel - - --Activated by clicking on function click_toggleControl(_, color) - if permissionCheck(color) then - if not controlActive then - --Activate control panel - controlActive = true - self.clearButtons() - createOpenCloseButton() - createSurfaceInput() - createSurfaceButtons() - createScaleInput() - createScaleButtons() - else - --Deactivate control panel - controlActive = false - self.clearButtons() - self.clearInputs() - createOpenCloseButton() - - end + if permissionCheck(color) then + if not controlActive then + --Activate control panel + controlActive = true + self.clearButtons() + createOpenCloseButton() + createSurfaceInput() + createSurfaceButtons() + createScaleInput() + createScaleButtons() + else + --Deactivate control panel + controlActive = false + self.clearButtons() + self.clearInputs() + createOpenCloseButton() end + end end - - - --Table surface control - - --Changes table surface function click_applySurface(_, color) - if permissionCheck(color) then - updateSurface() - broadcastToAll("New Table Image Applied", {0.2,0.9,0.2}) - end + if permissionCheck(color) then + updateSurface() + broadcastToAll("New Table Image Applied", { 0.2, 0.9, 0.2 }) + end end --Saves table surface function click_saveSurface(_, color) - if permissionCheck(color) then - local nickname = self.getInputs()[1].value - local url = self.getInputs()[2].value - if nickname == "" then - --No nickname - broadcastToAll("Please supply a nickname for this save.", {0.9,0.2,0.2}) - else - --Nickname exists + if permissionCheck(color) then + local nickname = self.getInputs()[1].value + local url = self.getInputs()[2].value + if nickname == "" then + --No nickname + broadcastToAll("Please supply a nickname for this save.", { 0.9, 0.2, 0.2 }) + else + --Nickname exists - if findInImageDataIndex(url, nickname) == nil then - --Save doesn't exist already - table.insert(tableImageData, {url=url, name=nickname}) - broadcastToAll("Image URL saved to memory.", {0.2,0.9,0.2}) - --Refresh buttons - self.clearButtons() - createOpenCloseButton() - createSurfaceButtons() - createScaleButtons() - else - --Save exists already - broadcastToAll("Memory already contains a save with this Name or URL. Delete it first.", {0.9,0.2,0.2}) - end - end - end -end - ---Loads table surface -function click_loadMemory(_, color, index) - if permissionCheck(color) then - self.editInput({index=0, value=tableImageData[index].name}) - self.editInput({index=1, value=tableImageData[index].url}) - updateSurface() - broadcastToAll("Table Image Loaded", {0.2,0.9,0.2}) - end -end - ---Deletes table surface -function click_deleteMemory(_, color, index) - if permissionCheck(color) then - table.remove(tableImageData, index) + if findInImageDataIndex(url, nickname) == nil then + --Save doesn't exist already + table.insert(tableImageData, { url = url, name = nickname }) + broadcastToAll("Image URL saved to memory.", { 0.2, 0.9, 0.2 }) + --Refresh buttons self.clearButtons() createOpenCloseButton() createSurfaceButtons() createScaleButtons() - broadcastToAll("Element Removed from Memory", {0.2,0.9,0.2}) + else + --Save exists already + broadcastToAll("Memory already contains a save with this Name or URL. Delete it first.", { 0.9, 0.2, 0.2 }) + end end + end +end + +--Loads table surface +function click_loadMemory(_, color, index) + if permissionCheck(color) then + self.editInput({ index = 0, value = tableImageData[index].name }) + self.editInput({ index = 1, value = tableImageData[index].url }) + updateSurface() + broadcastToAll("Table Image Loaded", { 0.2, 0.9, 0.2 }) + end +end + +--Deletes table surface +function click_deleteMemory(_, color, index) + if permissionCheck(color) then + table.remove(tableImageData, index) + self.clearButtons() + createOpenCloseButton() + createSurfaceButtons() + createScaleButtons() + broadcastToAll("Element Removed from Memory", { 0.2, 0.9, 0.2 }) + end end --Updates surface from the values in the input field function updateSurface() - local customInfo = obj_surface.getCustomObject() - customInfo.diffuse = self.getInputs()[2].value - obj_surface.setCustomObject(customInfo) - obj_surface = obj_surface.reload() + local customInfo = obj_surface.getCustomObject() + customInfo.diffuse = self.getInputs()[2].value + obj_surface.setCustomObject(customInfo) + obj_surface = obj_surface.reload() end - - --Table Scale control - - --Applies Scale to table pieces function click_applyScale(_, color) - if permissionCheck(color) then - local newWidth = tonumber(self.getInputs()[3].value) - local newDepth = tonumber(self.getInputs()[4].value) - if type(newWidth) ~= "number" then - broadcastToAll("Invalid Width", {0.9,0.2,0.2}) - return - elseif type(newDepth) ~= "number" then - broadcastToAll("Invalid Depth", {0.9,0.2,0.2}) - return - elseif newWidth<0.1 or newDepth<0.1 then - broadcastToAll("Scale cannot go below 0.1", {0.9,0.2,0.2}) - return - elseif newWidth>12 or newDepth>12 then - broadcastToAll("Scale should not go over 12 (world size limitation)", {0.9,0.2,0.2}) - return - else - changeTableScale(math.abs(newWidth), math.abs(newDepth)) - broadcastToAll("Scale applied.", {0.2,0.9,0.2}) - end + if permissionCheck(color) then + local newWidth = tonumber(self.getInputs()[3].value) + local newDepth = tonumber(self.getInputs()[4].value) + if type(newWidth) ~= "number" then + broadcastToAll("Invalid Width", { 0.9, 0.2, 0.2 }) + return + elseif type(newDepth) ~= "number" then + broadcastToAll("Invalid Depth", { 0.9, 0.2, 0.2 }) + return + elseif newWidth < 0.1 or newDepth < 0.1 then + broadcastToAll("Scale cannot go below 0.1", { 0.9, 0.2, 0.2 }) + return + elseif newWidth > 12 or newDepth > 12 then + broadcastToAll("Scale should not go over 12 (world size limitation)", { 0.9, 0.2, 0.2 }) + return + else + changeTableScale(math.abs(newWidth), math.abs(newDepth)) + broadcastToAll("Scale applied.", { 0.2, 0.9, 0.2 }) end + end end --Checks/unchecks move box for hands function click_checkMove(_, color) - if permissionCheck(color) then - local find_func = function(o) return o.click_function=="click_checkMove" end - if checkData.move == true then - checkData.move = false - local buttonEntry = findButton(self, find_func) - self.editButton({index=buttonEntry.index, label=""}) - else - checkData.move = true - local buttonEntry = findButton(self, find_func) - self.editButton({index=buttonEntry.index, label=string.char(10008)}) - end + if permissionCheck(color) then + local find_func = function(o) return o.click_function == "click_checkMove" end + if checkData.move == true then + checkData.move = false + local buttonEntry = findButton(self, find_func) + self.editButton({ index = buttonEntry.index, label = "" }) + else + checkData.move = true + local buttonEntry = findButton(self, find_func) + self.editButton({ index = buttonEntry.index, label = string.char(10008) }) end + end end --Checks/unchecks scale box for hands @@ -206,273 +190,343 @@ end --Alters scale of elements and moves them function changeTableScale(width, depth) - --Scaling factors used to translate scale to position offset - local width2pos = (width-1) * 18 - local depth2pos = (depth-1) * 18 + --Scaling factors used to translate scale to position offset + local width2pos = (width - 1) * 18 + local depth2pos = (depth - 1) * 18 - --Hand zone movement - if checkData.move == true then - for _, pc in ipairs(ref_playerColor) do - if Player[pc].getHandCount() > 0 then - moveHandZone(Player[pc], width2pos, depth2pos) - end - end + --Hand zone movement + if checkData.move == true then + for _, pc in ipairs(ref_playerColor) do + if Player[pc].getHandCount() > 0 then + moveHandZone(Player[pc], width2pos, depth2pos) + end end - --Hand zone scaling - --The button to enable this was disabled for technical reasons - if checkData.scale == true then - for _, pc in ipairs(ref_playerColor) do - if Player[pc].getHandCount() > 0 then - scaleHandZone(Player[pc], width, depth) - end - end + end + --Hand zone scaling + --The button to enable this was disabled for technical reasons + if checkData.scale == true then + for _, pc in ipairs(ref_playerColor) do + if Player[pc].getHandCount() > 0 then + scaleHandZone(Player[pc], width, depth) + end end + end - --Resizing table elements - obj_side_top.setScale({width, 1, 1}) - obj_side_bot.setScale({width, 1, 1}) - obj_side_lef.setScale({depth, 1, 1}) - obj_side_rig.setScale({depth, 1, 1}) - obj_surface.setScale({width, 1, depth}) + --Resizing table elements + obj_side_top.setScale({ width, 1, 1 }) + obj_side_bot.setScale({ width, 1, 1 }) + obj_side_lef.setScale({ depth, 1, 1 }) + obj_side_rig.setScale({ depth, 1, 1 }) + obj_surface.setScale({ width, 1, depth }) - --Moving table elements to accomodate new scale - obj_side_lef.setPosition({-width2pos,tableHeightOffset,0}) - obj_side_rig.setPosition({ width2pos,tableHeightOffset,0}) - obj_side_top.setPosition({0,tableHeightOffset, depth2pos}) - obj_side_bot.setPosition({0,tableHeightOffset,-depth2pos}) - obj_leg1.setPosition({-width2pos,tableHeightOffset,-depth2pos}) - obj_leg2.setPosition({-width2pos,tableHeightOffset, depth2pos}) - obj_leg3.setPosition({ width2pos,tableHeightOffset, depth2pos}) - obj_leg4.setPosition({ width2pos,tableHeightOffset,-depth2pos}) - self.setPosition(obj_leg4.positionToWorld({-22.12, 8.74,-19.16})) - --Only enabled when changing tableHeightOffset - --obj_surface.setPosition({0,tableHeightOffset,0}) + --Moving table elements to accomodate new scale + obj_side_lef.setPosition({ -width2pos, tableHeightOffset, 0 }) + obj_side_rig.setPosition({ width2pos, tableHeightOffset, 0 }) + obj_side_top.setPosition({ 0, tableHeightOffset, depth2pos }) + obj_side_bot.setPosition({ 0, tableHeightOffset, -depth2pos }) + obj_leg1.setPosition({ -width2pos, tableHeightOffset, -depth2pos }) + obj_leg2.setPosition({ -width2pos, tableHeightOffset, depth2pos }) + obj_leg3.setPosition({ width2pos, tableHeightOffset, depth2pos }) + obj_leg4.setPosition({ width2pos, tableHeightOffset, -depth2pos }) + self.setPosition(obj_leg4.positionToWorld({ -22.12, 8.74, -19.16 })) + --Only enabled when changing tableHeightOffset + --obj_surface.setPosition({0,tableHeightOffset,0}) end --Move hand zone, p=player reference, facts are scaling factors function moveHandZone(p, width2pos, depth2pos) - local widthX = obj_side_rig.getPosition().x - local depthZ = obj_side_top.getPosition().z - for i=1, p.getHandCount() do - local handT = p.getHandTransform() - local pos = handT.position - local y = handT.rotation.y + local widthX = obj_side_rig.getPosition().x + local depthZ = obj_side_top.getPosition().z + for i = 1, p.getHandCount() do + local handT = p.getHandTransform() + local pos = handT.position + local y = handT.rotation.y - if y<45 or y>320 or y>135 and y<225 then - if pos.z > 0 then - pos.z = pos.z + depth2pos - depthZ - else - pos.z = pos.z - depth2pos + depthZ - end - else - if pos.x > 0 then - pos.x = pos.x + width2pos - widthX - else - pos.x = pos.x - width2pos + widthX - end - end - - --Only enabled when changing tableHeightOffset - --pos.y = tableHeightOffset + 14 - - handT.position = pos - p.setHandTransform(handT, i) + if y < 45 or y > 320 or y > 135 and y < 225 then + if pos.z > 0 then + pos.z = pos.z + depth2pos - depthZ + else + pos.z = pos.z - depth2pos + depthZ + end + else + if pos.x > 0 then + pos.x = pos.x + width2pos - widthX + else + pos.x = pos.x - width2pos + widthX + end end -end + --Only enabled when changing tableHeightOffset + --pos.y = tableHeightOffset + 14 + + handT.position = pos + p.setHandTransform(handT, i) + end +end ---Scales hand zones, p=player reference, facts are scaling factors function scaleHandZone(p, width, depth) - local widthFact = width / obj_side_top.getScale().x - local depthFact = depth / obj_side_lef.getScale().x - for i=1, p.getHandCount() do - local handT = p.getHandTransform() - local scale = handT.scale - local y = handT.rotation.y - if y<45 or y>320 or y>135 and y<225 then - scale.x = scale.x * widthFact - else - scale.x = scale.x * depthFact - end - handT.scale = scale - p.setHandTransform(handT, i) + local widthFact = width / obj_side_top.getScale().x + local depthFact = depth / obj_side_lef.getScale().x + for i = 1, p.getHandCount() do + local handT = p.getHandTransform() + local scale = handT.scale + local y = handT.rotation.y + if y < 45 or y > 320 or y > 135 and y < 225 then + scale.x = scale.x * widthFact + else + scale.x = scale.x * depthFact end + handT.scale = scale + p.setHandTransform(handT, i) + end end - - --Information gathering - - --Checks if a color is promoted or host function permissionCheck(color) - if Player[color].host==true or Player[color].promoted==true then - return true - else - return false - end + if Player[color].host == true or Player[color].promoted == true then + return true + else + return false + end end --Locates a string saved within memory file function findInImageDataIndex(...) - for _, str in ipairs({...}) do - for i, v in ipairs(tableImageData) do - if v.url == str or v.name == str then - return i - end - end + for _, str in ipairs({ ... }) do + for i, v in ipairs(tableImageData) do + if v.url == str or v.name == str then + return i + end end - return nil + end + return nil end --Round number (num) to the Nth decimal (dec) function round(num, dec) - local mult = 10^(dec or 0) + local mult = 10 ^ (dec or 0) return math.floor(num * mult + 0.5) / mult end --Locates a button with a helper function function findButton(obj, func) - if func==nil then error("No func supplied to findButton") end - for _, v in ipairs(obj.getButtons()) do - if func(v) then - return v - end + if func == nil then error("No func supplied to findButton") end + for _, v in ipairs(obj.getButtons()) do + if func(v) then + return v end - return nil + end + return nil end - - --Creation of buttons/inputs - - function createOpenCloseButton() - local tooltip = "Open Table Control Panel" - if controlActive then - tooltip = "Close Table Control Panel" - end - self.createButton({ - click_function="click_toggleControl", function_owner=self, - position={0,0,0}, rotation={-45,0,0}, height=400, width=400, - color={1,1,1,0}, tooltip=tooltip - }) + local tooltip = "Open Table Control Panel" + if controlActive then + tooltip = "Close Table Control Panel" + end + self.createButton({ + click_function = "click_toggleControl", + function_owner = self, + position = { 0, 0, 0 }, + rotation = { -45, 0, 0 }, + height = 400, + width = 400, + color = { 1, 1, 1, 0 }, + tooltip = tooltip + }) end function createSurfaceInput() - local currentURL = obj_surface.getCustomObject().diffuse - local nickname = "" - if findInImageDataIndex(currentURL) ~= nil then - nickname = tableImageData[findInImageDataIndex(currentURL)].name - end - self.createInput({ - label="Nickname", input_function="none", function_owner=self, - alignment=3, position={0,0,2}, height=224, width=4000, - font_size=200, tooltip="Enter nickname for table image (only used for save)", - value=nickname - }) - self.createInput({ - label="URL", input_function="none", function_owner=self, - alignment=3, position={0,0,3}, height=224, width=4000, - font_size=200, tooltip="Enter URL for tabletop image", - value=currentURL - }) + local currentURL = obj_surface.getCustomObject().diffuse + local nickname = "" + if findInImageDataIndex(currentURL) ~= nil then + nickname = tableImageData[findInImageDataIndex(currentURL)].name + end + self.createInput({ + label = "Nickname", + input_function = "none", + function_owner = self, + alignment = 3, + position = { 0, 0, 2 }, + height = 224, + width = 4000, + font_size = 200, + tooltip = "Enter nickname for table image (only used for save)", + value = nickname + }) + self.createInput({ + label = "URL", + input_function = "none", + function_owner = self, + alignment = 3, + position = { 0, 0, 3 }, + height = 224, + width = 4000, + font_size = 200, + tooltip = "Enter URL for tabletop image", + value = currentURL + }) end function createSurfaceButtons() - --Label + --Label + self.createButton({ + label = "Tabletop Surface Image", + click_function = "none", + position = { 0, 0, 1 }, + height = 0, + width = 0, + font_size = 300, + font_color = { 1, 1, 1 } + }) + --Functional + self.createButton({ + label = "Apply Image\nTo Table", + click_function = "click_applySurface", + function_owner = self, + tooltip = "Apply URL as table image", + position = { 2, 0, 4 }, + height = 440, + width = 1400, + font_size = 200, + }) + self.createButton({ + label = "Save Image\nTo Memory", + click_function = "click_saveSurface", + function_owner = self, + tooltip = "Record URL into memory (requires nickname)", + position = { -2, 0, 4 }, + height = 440, + width = 1400, + font_size = 200, + }) + --Label + self.createButton({ + label = "Load From Memory", + click_function = "none", + position = { 0, 0, 5.5 }, + height = 0, + width = 0, + font_size = 300, + font_color = { 1, 1, 1 } + }) + --Saves, created dynamically from memory file + for i, memoryEntry in ipairs(tableImageData) do + --Load + local funcName = i .. "loadMemory" + local func = function(x, y) click_loadMemory(x, y, i) end + self.setVar(funcName, func) self.createButton({ - label="Tabletop Surface Image", click_function="none", - position={0,0,1}, height=0, width=0, font_size=300, font_color={1,1,1} + label = memoryEntry.name, + click_function = funcName, + function_owner = self, + tooltip = memoryEntry.url, + font_size = 200, + position = { -0.6, 0, 6.5 + 0.5 * (i - 1) }, + height = 240, + width = 3300, }) - --Functional + --Delete + local funcName = i .. "deleteMemory" + local func = function(x, y) click_deleteMemory(x, y, i) end + self.setVar(funcName, func) self.createButton({ - label="Apply Image\nTo Table", click_function="click_applySurface", - function_owner=self, tooltip="Apply URL as table image", - position={2,0,4}, height=440, width=1400, font_size=200, + label = "DELETE", + click_function = funcName, + function_owner = self, + tooltip = "", + position = { 3.6, 0, 6.5 + 0.5 * (i - 1) }, + height = 240, + width = 600, + font_size = 160, + font_color = { 1, 0, 0 }, + color = { 0.8, 0.8, 0.8 } }) - self.createButton({ - label="Save Image\nTo Memory", click_function="click_saveSurface", - function_owner=self, tooltip="Record URL into memory (requires nickname)", - position={-2,0,4}, height=440, width=1400, font_size=200, - }) - --Label - self.createButton({ - label="Load From Memory", click_function="none", - position={0,0,5.5}, height=0, width=0, font_size=300, font_color={1,1,1} - }) - --Saves, created dynamically from memory file - for i, memoryEntry in ipairs(tableImageData) do - --Load - local funcName = i.."loadMemory" - local func = function(x,y) click_loadMemory(x,y,i) end - self.setVar(funcName, func) - self.createButton({ - label=memoryEntry.name, click_function=funcName, - function_owner=self, tooltip=memoryEntry.url, font_size=200, - position={-0.6,0,6.5+0.5*(i-1)}, height=240, width=3300, - }) - --Delete - local funcName = i.."deleteMemory" - local func = function(x,y) click_deleteMemory(x,y,i) end - self.setVar(funcName, func) - self.createButton({ - label="DELETE", click_function=funcName, - function_owner=self, tooltip="", - position={3.6,0,6.5+0.5*(i-1)}, height=240, width=600, - font_size=160, font_color={1,0,0}, color={0.8,0.8,0.8} - }) - end + end end function createScaleInput() - self.createInput({ - label=string.char(8644), input_function="none", function_owner=self, - alignment=3, position={-8.5,0,2}, height=224, width=400, - font_size=200, tooltip="Table Width", - value=round(obj_side_top.getScale().x, 1) - }) - self.createInput({ - label=string.char(8645), input_function="none", function_owner=self, - alignment=3, position={-7.5,0,2}, height=224, width=400, - font_size=200, tooltip="Table Depth", - value=round(obj_side_lef.getScale().x, 1) - }) + self.createInput({ + label = string.char(8644), + input_function = "none", + function_owner = self, + alignment = 3, + position = { -8.5, 0, 2 }, + height = 224, + width = 400, + font_size = 200, + tooltip = "Table Width", + value = round(obj_side_top.getScale().x, 1) + }) + self.createInput({ + label = string.char(8645), + input_function = "none", + function_owner = self, + alignment = 3, + position = { -7.5, 0, 2 }, + height = 224, + width = 400, + font_size = 200, + tooltip = "Table Depth", + value = round(obj_side_lef.getScale().x, 1) + }) end function createScaleButtons() - --Labels - self.createButton({ - label="Table Scale", click_function="none", - position={-8,0,1}, height=0, width=0, font_size=300, font_color={1,1,1} - }) - self.createButton({ - label=string.char(8644).." "..string.char(8645), - click_function="none", - position={-8,0,2}, height=0, width=0, font_size=300, font_color={1,1,1} - }) - self.createButton({ - label="Move Hands:", click_function="none", - position={-8.3,0,3}, height=0, width=0, font_size=200, font_color={1,1,1} - }) - --Disabled due to me removing the feature for technical reasons - --[[ + --Labels + self.createButton({ + label = "Table Scale", + click_function = "none", + position = { -8, 0, 1 }, + height = 0, + width = 0, + font_size = 300, + font_color = { 1, 1, 1 } + }) + self.createButton({ + label = string.char(8644) .. " " .. string.char(8645), + click_function = "none", + position = { -8, 0, 2 }, + height = 0, + width = 0, + font_size = 300, + font_color = { 1, 1, 1 } + }) + self.createButton({ + label = "Move Hands:", + click_function = "none", + position = { -8.3, 0, 3 }, + height = 0, + width = 0, + font_size = 200, + font_color = { 1, 1, 1 } + }) + --Disabled due to me removing the feature for technical reasons + --[[ self.createButton({ label="Scale Hands:", click_function="none", position={-8.3,0,4}, height=0, width=0, font_size=200, font_color={1,1,1} }) ]] - --Checkboxes - local label = "" - if checkData.move == true then label = string.char(10008) end - self.createButton({ - label=label, click_function="click_checkMove", - function_owner=self, tooltip="Check to move hands when table is rescaled", - position={-6.8,0,3}, height=224, width=224, font_size=200, - }) - --[[ + --Checkboxes + local label = "" + if checkData.move == true then label = string.char(10008) end + self.createButton({ + label = label, + click_function = "click_checkMove", + function_owner = self, + tooltip = "Check to move hands when table is rescaled", + position = { -6.8, 0, 3 }, + height = 224, + width = 224, + font_size = 200, + }) + --[[ local label = "" if checkData.scale == true then label = string.char(10008) end self.createButton({ @@ -481,31 +535,29 @@ function createScaleButtons() position={-6.8,0,4}, height=224, width=224, font_size=200, }) ]] - --Apply button - self.createButton({ - label="Apply Scale", click_function="click_applyScale", - function_owner=self, tooltip="Apply width/depth to table", - position={-8,0,4}, height=440, width=1400, font_size=200, - }) + --Apply button + self.createButton({ + label = "Apply Scale", + click_function = "click_applyScale", + function_owner = self, + tooltip = "Apply width/depth to table", + position = { -8, 0, 4 }, + height = 440, + width = 1400, + font_size = 200, + }) end - - - - --Data tables - - - ref_noninteractable = { - "afc863","c8edca","393bf7","12c65e","f938a2","9f95fd","35b95f", - "5af8f2","4ee1f2","bd69bd" + "afc863", "c8edca", "393bf7", "12c65e", "f938a2", "9f95fd", "35b95f", + "5af8f2", "4ee1f2", "bd69bd" } ref_playerColor = { - "White", "Brown", "Red", "Orange", "Yellow", - "Green", "Teal", "Blue", "Purple", "Pink", "Black" + "White", "Brown", "Red", "Orange", "Yellow", + "Green", "Teal", "Blue", "Purple", "Pink", "Black" } --Dummy function, absorbs unwanted triggers diff --git a/objects/LuaScriptState.luascriptstate b/objects/LuaScriptState.luascriptstate index 87386952..99a91195 100644 --- a/objects/LuaScriptState.luascriptstate +++ b/objects/LuaScriptState.luascriptstate @@ -1 +1 @@ -{"acknowledgedUpgradeVersions":[],"chaosTokensGUID":[],"optionPanel":{"cardLanguage":"en","changePlayAreaImage":false,"enableCardHelpers":false,"playAreaConnectionColor":{"a":1,"b":0.4,"g":0.4,"r":0.4},"playAreaConnections":true,"playAreaSnapTags":true,"showAttachmentHelper":false,"showCleanUpHelper":false,"showCYOA":false,"showDisplacementTool":false,"showDrawButton":false,"showHandHelper":false,"showSearchAssistant":false,"showTitleSplash":true,"useClueClickers":false,"useResourceCounters":"disabled","useSnapTags":true}} +{"acknowledgedUpgradeVersions":[],"chaosTokensGUID":[],"optionPanel":{"cardLanguage":"en","changePlayAreaImage":false,"enableCardHelpers":false,"playAreaConnectionColor":{"a":1,"b":0.4,"g":0.4,"r":0.4},"playAreaConnections":true,"playAreaSnapTags":true,"showAttachmentHelper":false,"showCleanUpHelper":false,"showCYOA":false,"showDisplacementTool":false,"showDrawButton":false,"showHandHelper":false,"showSearchAssistant":false,"showTitleSplash":true,"useClassTexture":true,"useClueClickers":false,"useResourceCounters":"disabled","useSnapTags":true}} diff --git a/objects/OptionPanelSource.830bd0/DisplacementTool.0f1374.json b/objects/OptionPanelSource.830bd0/DisplacementTool.0f1374.json index 13264b54..02ad025d 100644 --- a/objects/OptionPanelSource.830bd0/DisplacementTool.0f1374.json +++ b/objects/OptionPanelSource.830bd0/DisplacementTool.0f1374.json @@ -22,7 +22,7 @@ "ImageURL": "http://cloud-3.steamusercontent.com/ugc/1915746489209870095/5F6A6F2946DBEB81667C15B112F9E35943E61A97/", "WidthScale": 0 }, - "Description": "Moves all objects on the playmat in the chosen direction.", + "Description": "Moves all objects on the playermat in the chosen direction.", "DragSelectable": true, "GMNotes": "", "GUID": "0f1374", diff --git a/objects/OptionPanelSource.830bd0/SearchAssistant.17aed0.json b/objects/OptionPanelSource.830bd0/SearchAssistant.17aed0.json index ff58f589..13ea7e9a 100644 --- a/objects/OptionPanelSource.830bd0/SearchAssistant.17aed0.json +++ b/objects/OptionPanelSource.830bd0/SearchAssistant.17aed0.json @@ -22,7 +22,7 @@ "ImageURL": "http://cloud-3.steamusercontent.com/ugc/1838053776205435595/ECFB88938ADBD1EF7AEF713111A11330FD9FAA5A/", "WidthScale": 0 }, - "Description": "Searches the top X cards of the nearest playmat by setting your hand aside and putting the cards into your hand.\n\nPut the target of your search on your set aside hand.", + "Description": "Searches the top X cards of the nearest playermat by setting your hand aside and putting the cards into your hand.\n\nPut the target of your search on your set aside hand.", "DragSelectable": true, "GMNotes": "", "GUID": "17aed0", diff --git a/objects/PlaymatImageSwapper.b7b45b.json b/objects/PlayAreaImageSwapper.b7b45b.json similarity index 88% rename from objects/PlaymatImageSwapper.b7b45b.json rename to objects/PlayAreaImageSwapper.b7b45b.json index 9cf1a047..f259acef 100644 --- a/objects/PlaymatImageSwapper.b7b45b.json +++ b/objects/PlayAreaImageSwapper.b7b45b.json @@ -22,7 +22,7 @@ "ImageURL": "https://i.imgur.com/gs1mtXJ.png", "WidthScale": 0 }, - "Description": "Allows changing of the playmat image. Provide URL to the image or leave empty for default image.", + "Description": "Allows changing of the playarea image. Provide URL to the image or leave empty for default image.", "DragSelectable": true, "GMNotes": "", "GUID": "b7b45b", @@ -37,7 +37,7 @@ "LuaScriptState": "{\"selectionIndex\":1,\"typeIndex\":1}", "MeasureMovement": false, "Name": "Custom_Token", - "Nickname": "Playmat Image Swapper", + "Nickname": "PlayArea Image Swapper", "Snap": true, "Sticky": true, "Tags": [ diff --git a/objects/Playermat1White.8b081b.json b/objects/Playermat1White.8b081b.json index c1d4fb6d..0eaea951 100644 --- a/objects/Playermat1White.8b081b.json +++ b/objects/Playermat1White.8b081b.json @@ -353,7 +353,7 @@ "IgnoreFoW": false, "LayoutGroupSortIndex": 0, "Locked": true, - "LuaScript": "require(\"playermat/Playmat\")", + "LuaScript": "require(\"playermat/Playermat\")", "LuaScriptState_path": "Playermat1White.8b081b.luascriptstate", "MeasureMovement": false, "Memo": "White", diff --git a/objects/Playermat1White.8b081b.luascriptstate b/objects/Playermat1White.8b081b.luascriptstate index ec466f0b..37f3fb4a 100644 --- a/objects/Playermat1White.8b081b.luascriptstate +++ b/objects/Playermat1White.8b081b.luascriptstate @@ -1 +1 @@ -{"activeInvestigatorClass":"Neutral","activeInvestigatorId":"00000","isDrawButtonVisible":false,"playerColor":"White","slotData":["any","any","any","Tarot","Hand (left)","Hand (right)","Ally","any","any","any","Accessory","Arcane","Arcane","Body"]} +{"activeInvestigatorClass":"Neutral","activeInvestigatorId":"00000","isClassTextureEnabled":true,"isDrawButtonVisible":false,"playerColor":"White","slotData":["any","any","any","Tarot","Hand (left)","Hand (right)","Ally","any","any","any","Accessory","Arcane","Arcane","Body"]} diff --git a/objects/Playermat2Orange.bd0ff4.json b/objects/Playermat2Orange.bd0ff4.json index 38973e7a..d2fb2b64 100644 --- a/objects/Playermat2Orange.bd0ff4.json +++ b/objects/Playermat2Orange.bd0ff4.json @@ -353,7 +353,7 @@ "IgnoreFoW": false, "LayoutGroupSortIndex": 0, "Locked": true, - "LuaScript": "require(\"playermat/Playmat\")", + "LuaScript": "require(\"playermat/Playermat\")", "LuaScriptState_path": "Playermat2Orange.bd0ff4.luascriptstate", "MeasureMovement": false, "Memo": "Orange", diff --git a/objects/Playermat2Orange.bd0ff4.luascriptstate b/objects/Playermat2Orange.bd0ff4.luascriptstate index c5d912d1..82227cf3 100644 --- a/objects/Playermat2Orange.bd0ff4.luascriptstate +++ b/objects/Playermat2Orange.bd0ff4.luascriptstate @@ -1 +1 @@ -{"activeInvestigatorClass":"Neutral","activeInvestigatorId":"00000","isDrawButtonVisible":false,"playerColor":"Orange","slotData":["any","any","any","Tarot","Hand (left)","Hand (right)","Ally","any","any","any","Accessory","Arcane","Arcane","Body"]} +{"activeInvestigatorClass":"Neutral","activeInvestigatorId":"00000","isClassTextureEnabled":true,"isDrawButtonVisible":false,"playerColor":"Orange","slotData":["any","any","any","Tarot","Hand (left)","Hand (right)","Ally","any","any","any","Accessory","Arcane","Arcane","Body"]} diff --git a/objects/Playermat3Green.383d8b.json b/objects/Playermat3Green.383d8b.json index b1a53642..41f250bc 100644 --- a/objects/Playermat3Green.383d8b.json +++ b/objects/Playermat3Green.383d8b.json @@ -353,7 +353,7 @@ "IgnoreFoW": false, "LayoutGroupSortIndex": 0, "Locked": true, - "LuaScript": "require(\"playermat/Playmat\")", + "LuaScript": "require(\"playermat/Playermat\")", "LuaScriptState_path": "Playermat3Green.383d8b.luascriptstate", "MeasureMovement": false, "Memo": "Green", diff --git a/objects/Playermat3Green.383d8b.luascriptstate b/objects/Playermat3Green.383d8b.luascriptstate index 9cc6512e..3f44af1d 100644 --- a/objects/Playermat3Green.383d8b.luascriptstate +++ b/objects/Playermat3Green.383d8b.luascriptstate @@ -1 +1 @@ -{"activeInvestigatorClass":"Neutral","activeInvestigatorId":"00000","isDrawButtonVisible":false,"playerColor":"Green","slotData":["any","any","any","Tarot","Hand (left)","Hand (right)","Ally","any","any","any","Accessory","Arcane","Arcane","Body"]} +{"activeInvestigatorClass":"Neutral","activeInvestigatorId":"00000","isClassTextureEnabled":true,"isDrawButtonVisible":false,"playerColor":"Green","slotData":["any","any","any","Tarot","Hand (left)","Hand (right)","Ally","any","any","any","Accessory","Arcane","Arcane","Body"]} diff --git a/objects/Playermat4Red.0840d5.json b/objects/Playermat4Red.0840d5.json index 2a14cd0c..c76a35b0 100644 --- a/objects/Playermat4Red.0840d5.json +++ b/objects/Playermat4Red.0840d5.json @@ -353,7 +353,7 @@ "IgnoreFoW": false, "LayoutGroupSortIndex": 0, "Locked": true, - "LuaScript": "require(\"playermat/Playmat\")", + "LuaScript": "require(\"playermat/Playermat\")", "LuaScriptState_path": "Playermat4Red.0840d5.luascriptstate", "MeasureMovement": false, "Memo": "Red", diff --git a/objects/Playermat4Red.0840d5.luascriptstate b/objects/Playermat4Red.0840d5.luascriptstate index 71a6f128..74f4e1f9 100644 --- a/objects/Playermat4Red.0840d5.luascriptstate +++ b/objects/Playermat4Red.0840d5.luascriptstate @@ -1 +1 @@ -{"activeInvestigatorClass":"Neutral","activeInvestigatorId":"00000","isDrawButtonVisible":false,"playerColor":"Red","slotData":["any","any","any","Tarot","Hand (left)","Hand (right)","Ally","any","any","any","Accessory","Arcane","Arcane","Body"]} +{"activeInvestigatorClass":"Neutral","activeInvestigatorId":"00000","isClassTextureEnabled":true,"isDrawButtonVisible":false,"playerColor":"Red","slotData":["any","any","any","Tarot","Hand (left)","Hand (right)","Ally","any","any","any","Accessory","Arcane","Arcane","Body"]} diff --git a/objects/TokenSource.124381/UniversalActionAbilityToken.834ad5.json b/objects/TokenSource.124381/UniversalActionAbilityToken.834ad5.json index e30872cc..d7142a26 100644 --- a/objects/TokenSource.124381/UniversalActionAbilityToken.834ad5.json +++ b/objects/TokenSource.124381/UniversalActionAbilityToken.834ad5.json @@ -41,7 +41,7 @@ "LayoutGroupSortIndex": 0, "Locked": false, "LuaScript": "require(\"core/UniversalActionAbilityToken\")", - "LuaScriptState": "", + "LuaScriptState": "{\"class\":\"Neutral\",\"symbol\":\"Neutral\"}", "MeasureMovement": false, "Memo": "universalActionAbility", "Name": "Custom_Tile", diff --git a/src/accessories/CampaignImporterExporter.ttslua b/src/accessories/CampaignImporterExporter.ttslua index 4d9a51b5..41eb9bd7 100644 --- a/src/accessories/CampaignImporterExporter.ttslua +++ b/src/accessories/CampaignImporterExporter.ttslua @@ -4,7 +4,7 @@ local deckImporterApi = require("arkhamdb/DeckImporterApi") local guidReferenceApi = require("core/GUIDReferenceApi") local optionPanelApi = require("core/OptionPanelApi") local playAreaApi = require("core/PlayAreaApi") -local playmatApi = require("playermat/PlaymatApi") +local playermatApi = require("playermat/PlayermatApi") -- base data for token creation local campaignTokenData = { @@ -95,7 +95,7 @@ function importFromToken(coin) Wait.condition( function() - local campaignBox = getObjectFromGUID(importData["box"]) + campaignBox = getObjectFromGUID(importData["box"]) if #campaignBox.getObjects() > 0 then placeCampaignFromToken(importData, coin) else @@ -103,11 +103,11 @@ function importFromToken(coin) end end, function() - local obj = getObjectFromGUID(importData["box"]) - if obj == nil then + campaignBox = getObjectFromGUID(importData["box"]) + if campaignBox == nil then return false else - return obj.type == "Bag" + return campaignBox.type == "Bag" end end, 2, @@ -190,10 +190,10 @@ function restoreCampaignData(importData, coin) playAreaApi.updateSurface(importData["playarea"]) playAreaApi.setInvestigatorCount(importData["clueCount"]) - -- restore Playmat slots + -- restore playermat slots if importData["slotData"] then for matColor, slotData in pairs(importData["slotData"]) do - playmatApi.loadSlotData(matColor, slotData) + playermatApi.loadSlotData(matColor, slotData) end end @@ -272,10 +272,10 @@ function createCampaignToken(_, playerColor, _) table.insert(campaignTokenData.ContainedObjects, indexData) end - -- get the slot symbol data for each playmat (use GUIDReferenceApi to only get this for existing playmats) + -- get the slot symbol data for each playermat (use GUIDReferenceApi to only get this for existing playermats) campaignData.slotData = {} for matColor, _ in pairs(guidReferenceApi.getObjectsByType("Playermat")) do - local slotData = playmatApi.getSlotData(matColor) + local slotData = playermatApi.getSlotData(matColor) campaignData.slotData[matColor] = slotData end @@ -306,7 +306,7 @@ end function setTrauma(trauma) for i, matColor in ipairs({ "White", "Orange", "Green", "Red" }) do - playmatApi.updateCounter(matColor, "DamageCounter", trauma[i]) - playmatApi.updateCounter(matColor, "HorrorCounter", trauma[i + 4]) + playermatApi.updateCounter(matColor, "DamageCounter", trauma[i]) + playermatApi.updateCounter(matColor, "HorrorCounter", trauma[i + 4]) end end diff --git a/src/accessories/CleanUpHelper.ttslua b/src/accessories/CleanUpHelper.ttslua index 5a0f5364..e43a79e7 100644 --- a/src/accessories/CleanUpHelper.ttslua +++ b/src/accessories/CleanUpHelper.ttslua @@ -1,6 +1,6 @@ -- Cleans up the table for the next scenario in a campaign: -- sets counters to default values (resources and doom) or trauma values (health and sanity, if not disabled) from campaign log --- puts everything on playmats and hands into respective trashcans +-- puts everything on playermats and hands into respective trashcans -- use the IGNORE_TAG to exclude objects from tidying (default: "CleanUpHelper_Ignore") local blessCurseManagerApi = require("chaosbag/BlessCurseManagerApi") @@ -8,7 +8,7 @@ local chaosBagApi = require("chaosbag/ChaosBagApi") local guidReferenceApi = require("core/GUIDReferenceApi") local mythosAreaApi = require("core/MythosAreaApi") local playAreaApi = require("core/PlayAreaApi") -local playmatApi = require("playermat/PlaymatApi") +local playermatApi = require("playermat/PlayermatApi") local searchLib = require("util/SearchLib") local soundCubeApi = require("core/SoundCubeApi") local tokenSpawnTrackerApi = require("core/token/TokenSpawnTrackerApi") @@ -28,9 +28,9 @@ options["importTrauma"] = true options["tidyPlayermats"] = true options["removeDrawnLines"] = false --- don't clean playmats for preludes +-- don't clean playermats for preludes local scenarioName -local preludeList = { +local preludeList = { ["Prelude: Welcome to Hemlock Vale!"] = true } @@ -149,13 +149,13 @@ end function updateCounters() if not getOptionValue() then return end - playmatApi.updateCounter("All", "ResourceCounter", 5) - playmatApi.updateCounter("All", "ClickableClueCounter", 0) - playmatApi.resetSkillTracker("All") + playermatApi.updateCounter("All", "ResourceCounter", 5) + playermatApi.updateCounter("All", "ClickableClueCounter", 0) + playermatApi.resetSkillTracker("All") for i = 1, 4 do - playmatApi.updateCounter(COLORS[i], "DamageCounter", RESET_VALUES.Damage[i]) - playmatApi.updateCounter(COLORS[i], "HorrorCounter", RESET_VALUES.Horror[i]) + playermatApi.updateCounter(COLORS[i], "DamageCounter", RESET_VALUES.Damage[i]) + playermatApi.updateCounter(COLORS[i], "HorrorCounter", RESET_VALUES.Horror[i]) end end @@ -272,7 +272,7 @@ function discardHands() for i = 1, 4 do local trash = guidReferenceApi.getObjectByOwnerAndType(COLORS[i], "Trash") if trash == nil then return end - local hand = Player[playmatApi.getPlayerColor(COLORS[i])].getHandObjects() + local hand = Player[playermatApi.getPlayerColor(COLORS[i])].getHandObjects() for j = #hand, 1, -1 do trash.putObject(hand[j]) end @@ -340,7 +340,7 @@ function tidyPlayerMatCoroutine() -- get respective trash local trash = guidReferenceApi.getObjectByOwnerAndType(COLORS[i], "Trash") if trash == nil then - printToAll("Trashcan for " .. COLORS[i] .. " playmat could not be found! Skipping this playermat.", "Yellow") + printToAll("Trashcan for " .. COLORS[i] .. " playermat could not be found! Skipping this playermat.", "Yellow") goto continue end @@ -351,7 +351,7 @@ function tidyPlayerMatCoroutine() local objList if i < 5 then - objList = playmatApi.searchAroundPlaymat(COLORS[i]) + objList = playermatApi.searchAroundPlayermat(COLORS[i]) else -- Victory Display + Mythos Area objList = searchLib.inArea({ -2, 2, 10 }, { 0, 270, 0 }, { 55, 1, 13.5 }) diff --git a/src/accessories/HandHelper.ttslua b/src/accessories/HandHelper.ttslua index 7d8d97ef..8728388e 100644 --- a/src/accessories/HandHelper.ttslua +++ b/src/accessories/HandHelper.ttslua @@ -1,4 +1,4 @@ -local playmatApi = require("playermat/PlaymatApi") +local playermatApi = require("playermat/PlayermatApi") -- forward declaration of variables that are used across functions local matColor, handColor, hovering @@ -36,7 +36,7 @@ function onLoad() updateColors() -- start loop to update card count - playmatApi.checkForDES(matColor) + playermatApi.checkForDES(matColor) Wait.time(updateValue, 1, -1) end @@ -49,7 +49,7 @@ function onObjectHover(hoverColor, object) if object == self then hovering = true - playmatApi.checkForDES(matColor) + playermatApi.checkForDES(matColor) updateValue() else hovering = false @@ -58,8 +58,8 @@ end -- updates the matcolor and handcolor variable function updateColors() - matColor = playmatApi.getMatColorByPosition(self.getPosition()) - handColor = playmatApi.getPlayerColor(matColor) + matColor = playermatApi.getMatColorByPosition(self.getPosition()) + handColor = playermatApi.getPlayerColor(matColor) self.setName(handColor .. " Hand Helper") end @@ -74,7 +74,7 @@ function updateValue() if Player[handColor].getHandCount() == 0 then return end -- get state of "Dream-Enhancing Serum" from playermat - local hasDES = playmatApi.hasDES(matColor) + local hasDES = playermatApi.hasDES(matColor) -- default to regular count if hovered if hovering then @@ -113,5 +113,5 @@ end -- discards a random non-hidden card from hand function discardRandom() - playmatApi.doDiscardOne(matColor) + playermatApi.doDiscardOne(matColor) end diff --git a/src/accessories/PhaseTracker.ttslua b/src/accessories/PhaseTracker.ttslua index 066d3ad3..e646a004 100644 --- a/src/accessories/PhaseTracker.ttslua +++ b/src/accessories/PhaseTracker.ttslua @@ -11,9 +11,6 @@ local phaseImages = { "http://cloud-3.steamusercontent.com/ugc/982233321870237261/C287CAED2423970F33E72D6C7415CBEC6794C533/" } --- these are intentionally global for remote updating --- phaseId, broadcastChange - function onSave() return JSON.encode({ phaseId = phaseId, @@ -21,11 +18,15 @@ function onSave() }) end +function loadFromSaveTable(savedData) + for var, val in pairs(JSON.decode(savedData)) do + _G[var] = val + end +end + function onLoad(savedData) if savedData and savedData ~= "" then - local loadedData = JSON.decode(savedData) - phaseId = loadedData.phaseId - broadcastChange = loadedData.broadcastChange + loadFromSaveTable(savedData) else phaseId = 1 broadcastChange = false diff --git a/src/accessories/SearchAssistant.ttslua b/src/accessories/SearchAssistant.ttslua index bcedee2d..24872e73 100644 --- a/src/accessories/SearchAssistant.ttslua +++ b/src/accessories/SearchAssistant.ttslua @@ -1,16 +1,16 @@ local deckLib = require("util/DeckLib") -local playmatApi = require("playermat/PlaymatApi") +local playermatApi = require("playermat/PlayermatApi") local searchLib = require("util/SearchLib") -- forward declaration of variables that are used across functions local matColor, handColor, setAsidePosition, setAsideRotation, drawDeckPosition, topCardDetected -local quickParameters = {} -quickParameters.function_owner = self -quickParameters.font_size = 165 -quickParameters.width = 275 -quickParameters.height = 275 -quickParameters.color = "White" +local quickParameters = {} +quickParameters.function_owner = self +quickParameters.font_size = 165 +quickParameters.width = 275 +quickParameters.height = 275 +quickParameters.color = "White" -- common parameters local buttonParameters = {} @@ -20,17 +20,17 @@ buttonParameters.width = 650 buttonParameters.height = 225 buttonParameters.color = "White" -local inputParameters = {} -inputParameters.function_owner = self -inputParameters.input_function = "updateSearchNumber" -inputParameters.tooltip = "custom search amount" -inputParameters.label = "#" -inputParameters.font_size = 175 -inputParameters.width = 400 -inputParameters.height = inputParameters.font_size + 23 -inputParameters.position = { 0, 0.11, 0 } -inputParameters.alignment = 3 -inputParameters.validation = 2 +local inputParameters = {} +inputParameters.function_owner = self +inputParameters.input_function = "updateSearchNumber" +inputParameters.tooltip = "custom search amount" +inputParameters.label = "#" +inputParameters.font_size = 175 +inputParameters.width = 400 +inputParameters.height = inputParameters.font_size + 23 +inputParameters.position = { 0, 0.11, 0 } +inputParameters.alignment = 3 +inputParameters.validation = 2 function onLoad() normalView() @@ -101,12 +101,12 @@ end -- start the search (change UI, set handCards aside, draw cards) function startSearch(messageColor, number) - matColor = playmatApi.getMatColorByPosition(self.getPosition()) - handColor = playmatApi.getPlayerColor(matColor) + matColor = playermatApi.getMatColorByPosition(self.getPosition()) + handColor = playermatApi.getPlayerColor(matColor) topCardDetected = false -- get draw deck - local deckAreaObjects = playmatApi.getDeckAreaObjects(matColor) + local deckAreaObjects = playermatApi.getDeckAreaObjects(matColor) if deckAreaObjects.draw == nil then printToColor(matColor .. " draw deck could not be found!", messageColor, "Red") return @@ -117,17 +117,17 @@ function startSearch(messageColor, number) drawDeckPosition = bounds.center + Vector(0, bounds.size.y / 2 + 0.2, 0) printToColor("Place target(s) of search on set aside hand.", messageColor, "Green") - -- get playmat orientation + -- get playermat orientation local offset = -15 if matColor == "Orange" or matColor == "Red" then offset = 15 end -- get position and rotation for set aside cards - local handData = Player[handColor].getHandTransform() - local handCards = Player[handColor].getHandObjects() - setAsidePosition = handData.position + offset * handData.right - setAsideRotation = { handData.rotation.x, handData.rotation.y + 180, 180 } + local handData = Player[handColor].getHandTransform() + local handCards = Player[handColor].getHandObjects() + setAsidePosition = handData.position + offset * handData.right + setAsideRotation = { handData.rotation.x, handData.rotation.y + 180, 180 } -- set y-value setAsidePosition.y = 1.5 @@ -146,7 +146,7 @@ function startSearch(messageColor, number) searchView() Wait.time(function() - deckAreaObjects = playmatApi.getDeckAreaObjects(matColor) + deckAreaObjects = playermatApi.getDeckAreaObjects(matColor) deckAreaObjects.draw.deal(number, handColor) end, 1) end @@ -175,7 +175,7 @@ function endSearch(_, _, isRightClick) -- delay is to wait for cards to enter deck if not isRightClick then Wait.time(function() - local deckAreaObjects = playmatApi.getDeckAreaObjects(matColor) + local deckAreaObjects = playermatApi.getDeckAreaObjects(matColor) if deckAreaObjects.draw then deckAreaObjects.draw.shuffle() end @@ -184,6 +184,6 @@ function endSearch(_, _, isRightClick) -- Norman Withers handling if topCardDetected then - Wait.time(function() playmatApi.flipTopCardFromDeck(matColor) end, #handCards * 0.3 + 0.75) + Wait.time(function() playermatApi.flipTopCardFromDeck(matColor) end, #handCards * 0.3 + 0.75) end end diff --git a/src/accessories/UnderworldMarketHelper.ttslua b/src/accessories/UnderworldMarketHelper.ttslua index 0f851682..0373efbb 100644 --- a/src/accessories/UnderworldMarketHelper.ttslua +++ b/src/accessories/UnderworldMarketHelper.ttslua @@ -1,277 +1,275 @@ local searchLib = require("util/SearchLib") -function onload(savedData) - revealCardPositions = { - Vector(3.5, 0.25, 0), - Vector(-3.5, 0.25, 0) - } - - revealCardPositionsSwap = { - Vector(-3.5, 0.25, 0), - Vector(3.5, 0.25, 0) - } - - self.createButton({ - label = 'Underworld Market\nHelper', - click_function = "none", - function_owner = self, - position = {0,-0.1,-1.6}, - height = 0, - width = 0, - font_size = 145, - font_color = {1,1,1} - }) - - hiddenCards = 10 - hiddenCardLabel = '-----' - - isSetup = false - movingCards = false - - self.addContextMenuItem('Reset helper', resetHelper) - - if savedData ~= '' then - local loaded_data = JSON.decode(savedData) - hiddenCards = loaded_data.saved_hiddenCards - - isSetup = true - refreshButtons() - end +function onSave() + return JSON.encode({ saved_hiddenCards = hiddenCards }) end -function onSave() - return JSON.encode({ - saved_hiddenCards = hiddenCards - }) +function onload(savedData) + revealCardPositions = { + Vector(3.5, 0.25, 0), + Vector(-3.5, 0.25, 0) + } + + revealCardPositionsSwap = { + Vector(-3.5, 0.25, 0), + Vector(3.5, 0.25, 0) + } + + self.createButton({ + label = 'Underworld Market\nHelper', + click_function = "none", + function_owner = self, + position = { 0, -0.1, -1.6 }, + height = 0, + width = 0, + font_size = 145, + font_color = { 1, 1, 1 } + }) + + hiddenCards = 10 + hiddenCardLabel = '-----' + + isSetup = false + movingCards = false + + self.addContextMenuItem('Reset helper', resetHelper) + + if savedData and savedData ~= '' then + local loaded_data = JSON.decode(savedData) + hiddenCards = loaded_data.saved_hiddenCards + + isSetup = true + refreshButtons() + end end function onObjectEnterContainer(container, object) - if container ~= self then return end + if container ~= self then return end - if isSetup and object.tag == "Card" then - refreshButtons() - end + if isSetup and object.tag == "Card" then + refreshButtons() + end - if object.tag == "Deck" then - if validateDeck(object) then - takeDeckOut(object.getGUID(), self.getPosition() + Vector(0, 0.1, 0)) - refreshButtons() - - isSetup = true - end - elseif object.tag ~= "Card" then - broadcastToAll("The 'Underworld Market Helper' is meant to be used for cards.", "White") + if object.tag == "Deck" then + if validateDeck(object) then + takeDeckOut(object.getGUID(), self.getPosition() + Vector(0, 0.1, 0)) + refreshButtons() + + isSetup = true end + elseif object.tag ~= "Card" then + broadcastToAll("The 'Underworld Market Helper' is meant to be used for cards.", "White") + end end function onObjectLeaveContainer(container, object) - if container ~= self then return end - - if isSetup then - refreshButtons() - end + if container ~= self then return end + + if isSetup then + refreshButtons() + end end function validateDeck(deck) - if deck.getQuantity() ~= 10 then - print('Underworld Market Helper: Deck must include exactly 10 cards.') - return false + if deck.getQuantity() ~= 10 then + print('Underworld Market Helper: Deck must include exactly 10 cards.') + return false + end + + local illicitCount = 0 + + for _, card in ipairs(deck.getObjects()) do + decodedGMNotes = JSON.decode(card.gm_notes) + + if decodedGMNotes ~= nil and string.find(decodedGMNotes.traits, "Illicit", 1, true) then + illicitCount = illicitCount + 1 end + end - local illicitCount = 0 + if illicitCount ~= 10 then + print('Underworld Market Helper: Deck must include 10 Illicit cards.') + return false + end - for _, card in ipairs(deck.getObjects()) do - decodedGMNotes = JSON.decode(card.gm_notes) - - if decodedGMNotes ~= nil and string.find(decodedGMNotes.traits, "Illicit", 1, true) then - illicitCount = illicitCount + 1 - end - end - - if illicitCount ~= 10 then - print('Underworld Market Helper: Deck must include 10 Illicit cards.') - return false - end - - return true + return true end function refreshButtons() - local cardsList = '' + local cardsList = '' - for i, card in ipairs(self.getObjects()) do - local localCardName = card.name + for i, card in ipairs(self.getObjects()) do + local localCardName = card.name - if i <= hiddenCards then - localCardName = hiddenCardLabel - end - - cardsList = cardsList .. localCardName .. '\n' + if i <= hiddenCards then + localCardName = hiddenCardLabel end - self.clearButtons() + cardsList = cardsList .. localCardName .. '\n' + end - self.createButton({ - label = 'Market Deck:', - click_function = "none", - function_owner = self, - position = {0,-0.1,-1.6}, - height = 0, - width = 0, - font_size = 150, - font_color = {1,1,1} - }) + self.clearButtons() - self.createButton({ - label = cardsList, - click_function = "none", - function_owner = self, - position = {0,-0.1,0.15}, - height = 0, - width = 0, - font_size = 115, - font_color = {1,1,1} - }) + self.createButton({ + label = 'Market Deck:', + click_function = "none", + function_owner = self, + position = { 0, -0.1, -1.6 }, + height = 0, + width = 0, + font_size = 150, + font_color = { 1, 1, 1 } + }) - self.createButton({ - click_function = 'revealFirstTwoCards', - function_owner = self, - label = 'Reveal', - position = {-0.85,0,1.6}, - width = 375, - height = 175, - font_size = 90 - }) + self.createButton({ + label = cardsList, + click_function = "none", + function_owner = self, + position = { 0, -0.1, 0.15 }, + height = 0, + width = 0, + font_size = 115, + font_color = { 1, 1, 1 } + }) - self.createButton({ - click_function = 'swap', - function_owner = self, - label = 'Swap', - position = {0,0,1.6}, - width = 375, - height = 175, - font_size = 90 - }) + self.createButton({ + click_function = 'revealFirstTwoCards', + function_owner = self, + label = 'Reveal', + position = { -0.85, 0, 1.6 }, + width = 375, + height = 175, + font_size = 90 + }) - self.createButton({ - click_function = 'finish', - function_owner = self, - label = 'Finish', - position = {0.85,0,1.6}, - width = 375, - height = 175, - font_size = 90 - }) + self.createButton({ + click_function = 'swap', + function_owner = self, + label = 'Swap', + position = { 0, 0, 1.6 }, + width = 375, + height = 175, + font_size = 90 + }) + + self.createButton({ + click_function = 'finish', + function_owner = self, + label = 'Finish', + position = { 0.85, 0, 1.6 }, + width = 375, + height = 175, + font_size = 90 + }) end function takeDeckOut(guid, pos) - local deck = self.takeObject({ guid = guid, position = pos, smooth = false }) + local deck = self.takeObject({ guid = guid, position = pos, smooth = false }) - for i = 1, #deck.getObjects() do - self.putObject(deck.takeObject({ position = pos + Vector(0, 0.1 * i, 0), smooth = false })) - end + for i = 1, #deck.getObjects() do + self.putObject(deck.takeObject({ position = pos + Vector(0, 0.1 * i, 0), smooth = false })) + end - self.shuffle() + self.shuffle() end function getRevealedCards() - local revealedCards = {} + local revealedCards = {} - for _, pos in ipairs(revealCardPositions) do - for _, obj in ipairs(searchLib.atPosition(self.positionToWorld(pos), "isCard")) do - table.insert(revealedCards, obj.getGUID()) - end + for _, pos in ipairs(revealCardPositions) do + for _, obj in ipairs(searchLib.atPosition(self.positionToWorld(pos), "isCard")) do + table.insert(revealedCards, obj.getGUID()) end + end - return revealedCards + return revealedCards end function revealFirstTwoCards() - if movingCards or #getRevealedCards() > 0 then return end + if movingCards or #getRevealedCards() > 0 then return end - for i, card in ipairs(self.getObjects()) do - movingCards = true + for i, card in ipairs(self.getObjects()) do + movingCards = true - self.takeObject({ - index = 0, - rotation = self.getRotation(), - position = self.positionToWorld(revealCardPositions[i]), - callback_function = function(obj) - obj.resting = true - movingCards = false - end - }) + self.takeObject({ + index = 0, + rotation = self.getRotation(), + position = self.positionToWorld(revealCardPositions[i]), + callback_function = function(obj) + obj.resting = true + movingCards = false + end + }) - hiddenCards = hiddenCards - 1 + hiddenCards = hiddenCards - 1 - if i == 2 or #self.getObjects() == 0 then - break - end + if i == 2 or #self.getObjects() == 0 then + break end + end - refreshButtons() + refreshButtons() end function swap() - if movingCards then return end + if movingCards then return end - local revealedCards = getRevealedCards() + local revealedCards = getRevealedCards() - if #revealedCards == 2 then - for i, revealedCardGUID in ipairs(revealedCards) do - local revealedCard = getObjectFromGUID(revealedCardGUID) + if #revealedCards == 2 then + for i, revealedCardGUID in ipairs(revealedCards) do + local revealedCard = getObjectFromGUID(revealedCardGUID) - revealedCard.setPositionSmooth(self.positionToWorld(revealCardPositionsSwap[i]), false, false) - end + revealedCard.setPositionSmooth(self.positionToWorld(revealCardPositionsSwap[i]), false, false) end + end end function finish() - if movingCards then return end + if movingCards then return end - local revealedCards = getRevealedCards() + local revealedCards = getRevealedCards() - movingCards = true + movingCards = true - for i, revealedCardGUID in ipairs(revealedCards) do - self.putObject(getObjectFromGUID(revealedCardGUID)) - end + for i, revealedCardGUID in ipairs(revealedCards) do + self.putObject(getObjectFromGUID(revealedCardGUID)) + end - Wait.time( - function() - movingCards = false - end, + Wait.time( + function() + movingCards = false + end, 0.75) end function resetHelper() - for i, card in ipairs(self.getObjects()) do - self.takeObject({ - index = 0, - smooth = false, - rotation = self.getRotation(), - position = self.positionToWorld(revealCardPositions[2]) - }) - end - - self.clearButtons() - - self.createButton({ - label = 'Underworld Market\nHelper', - click_function = "none", - function_owner = self, - position = {0,-0.1,-1.6}, - height = 0, - width = 0, - font_size = 145, - font_color = {1,1,1} + for i, card in ipairs(self.getObjects()) do + self.takeObject({ + index = 0, + smooth = false, + rotation = self.getRotation(), + position = self.positionToWorld(revealCardPositions[2]) }) + end - hiddenCards = 10 - isSetup = false - movingCards = false + self.clearButtons() - self.reset() + self.createButton({ + label = 'Underworld Market\nHelper', + click_function = "none", + function_owner = self, + position = { 0, -0.1, -1.6 }, + height = 0, + width = 0, + font_size = 145, + font_color = { 1, 1, 1 } + }) - print('Underworld Market Helper: Helper has been reset.') + hiddenCards = 10 + isSetup = false + movingCards = false + + self.reset() + + print('Underworld Market Helper: Helper has been reset.') end diff --git a/src/arkhamdb/ArkhamDb.ttslua b/src/arkhamdb/ArkhamDb.ttslua index 5ff08a63..f60d8e94 100644 --- a/src/arkhamdb/ArkhamDb.ttslua +++ b/src/arkhamdb/ArkhamDb.ttslua @@ -482,7 +482,6 @@ do ---@param uri table ---@param on_success fun(status, vararg): boolean, any ---@param on_error nil|fun(status, vararg): string - ---@vararg any ---@return Request function Request.start(uri, on_success, on_error, ...) local parameters = table.pack(...) @@ -497,7 +496,6 @@ do ---@param requests Request[] ---@param on_success fun(content: any, vararg: any) ---@param on_error fun(requests: Request, vararg: any)|nil - ---@vararg any function Request.with_all(requests, on_success, on_error, ...) local parameters = table.pack(...) diff --git a/src/arkhamdb/DeckImporter.ttslua b/src/arkhamdb/DeckImporter.ttslua index 0c5d4089..8619eec4 100644 --- a/src/arkhamdb/DeckImporter.ttslua +++ b/src/arkhamdb/DeckImporter.ttslua @@ -3,7 +3,7 @@ require("playercards/PlayerCardSpawner") local allCardsBagApi = require("playercards/AllCardsBagApi") local arkhamDb = require("arkhamdb/ArkhamDb") local guidReferenceApi = require("core/GUIDReferenceApi") -local playmatApi = require("playermat/PlaymatApi") +local playermatApi = require("playermat/PlayermatApi") local zones = require("playermat/Zones") local matsWithInvestigator = {} @@ -189,7 +189,7 @@ end function loadDecks() if not allCardsBagApi.isIndexReady() then return end - matsWithInvestigator = playmatApi.getUsedMatColors() + matsWithInvestigator = playermatApi.getUsedMatColors() if redDeckId ~= nil and redDeckId ~= "" then buildDeck("Red", redDeckId) end @@ -354,7 +354,7 @@ end ---@param deck tts__Object Callback-provided spawned deck object ---@param playerColor string Color of the player to draw the cards to function deckSpawned(deck, playerColor) - local player = Player[playmatApi.getPlayerColor(playerColor)] + local player = Player[playermatApi.getPlayerColor(playerColor)] local handPos = player.getHandTransform(1).position -- Only one hand zone per player local deckCards = deck.getData().ContainedObjects @@ -453,7 +453,7 @@ function removeBusyZones(playerColor, zoneDecks) -- check for existing deck local cardsInDeckArea = 0 - for _, obj in pairs(playmatApi.getDeckAreaObjects(playerColor)) do + for _, obj in pairs(playermatApi.getDeckAreaObjects(playerColor)) do cardsInDeckArea = cardsInDeckArea + #obj.getObjects() end @@ -732,7 +732,7 @@ end ---@param resourceModifier number Modifier for the starting resources function updateStartingResources(playerColor, resourceModifier) if resourceModifier ~= 0 then - playmatApi.updateCounter(playerColor, "ResourceCounter", _, resourceModifier) + playermatApi.updateCounter(playerColor, "ResourceCounter", _, resourceModifier) printToAll("Modified starting resources", playerColor) end end diff --git a/src/core/DataHelper.ttslua b/src/core/DataHelper.ttslua index 5845b09b..1f5bcd22 100644 --- a/src/core/DataHelper.ttslua +++ b/src/core/DataHelper.ttslua @@ -483,13 +483,12 @@ modeData = { } function onSave() - local globalState = JSON.encode(SPAWNED_PLAYER_CARD_GUIDS) - return globalState + return JSON.encode(SPAWNED_PLAYER_CARD_GUIDS) end -function onLoad(save_state) - if save_state ~= '' then - SPAWNED_PLAYER_CARD_GUIDS = JSON.decode(save_state) +function onLoad(savedData) + if savedData and savedData ~= '' then + SPAWNED_PLAYER_CARD_GUIDS = JSON.decode(savedData) else SPAWNED_PLAYER_CARD_GUIDS = {} end diff --git a/src/core/DoomInPlayCounter.ttslua b/src/core/DoomInPlayCounter.ttslua index 598f33d5..07029a75 100644 --- a/src/core/DoomInPlayCounter.ttslua +++ b/src/core/DoomInPlayCounter.ttslua @@ -1,10 +1,10 @@ local guidReferenceApi = require("core/GUIDReferenceApi") -local playmatApi = require("playermat/PlaymatApi") +local playermatApi = require("playermat/PlayermatApi") local ZONE, TRASH -local doomURL = "https://i.imgur.com/EoL7yaZ.png" -local IGNORE_TAG = "DoomCounter_ignore" -local TOTAL_PLAY_AREA = { +local doomURL = "https://i.imgur.com/EoL7yaZ.png" +local IGNORE_TAG = "DoomCounter_ignore" +local TOTAL_PLAY_AREA = { upperLeft = { x = -9, z = -35 @@ -66,15 +66,15 @@ end -- removes doom from playermats / playarea function removeDoom(options) if options.Playermats then - local count = removeDoomFromList(playmatApi.searchAroundPlaymat("All")) - if count > 0 then + local count = removeDoomFromList(playermatApi.searchAroundPlayermat("All")) + if count > 0 then broadcastToAll(count .. " doom removed from playermats.", "White") end end if options.Playarea then local count = removeDoomFromList(ZONE.getObjects()) - if count > 0 then + if count > 0 then broadcastToAll(count .. " doom removed from play area.", "White") end end @@ -96,7 +96,7 @@ end -- helper function to check if a position is inside an area function inArea(point, bounds) return (point.x < bounds.upperLeft.x - and point.x > bounds.lowerRight.x - and point.z > bounds.upperLeft.z - and point.z < bounds.lowerRight.z) + and point.x > bounds.lowerRight.x + and point.z > bounds.upperLeft.z + and point.z < bounds.lowerRight.z) end diff --git a/src/core/GameKeyHandler.ttslua b/src/core/GameKeyHandler.ttslua index b8ef7bf7..462f7216 100644 --- a/src/core/GameKeyHandler.ttslua +++ b/src/core/GameKeyHandler.ttslua @@ -2,7 +2,7 @@ local blessCurseManagerApi = require("chaosbag/BlessCurseManagerApi") local guidReferenceApi = require("core/GUIDReferenceApi") local navigationOverlayApi = require("core/NavigationOverlayApi") local optionPanelApi = require("core/OptionPanelApi") -local playmatApi = require("playermat/PlaymatApi") +local playermatApi = require("playermat/PlayermatApi") local searchLib = require("util/SearchLib") local victoryDisplayApi = require("core/VictoryDisplayApi") @@ -26,28 +26,28 @@ function onLoad() addHotkey("Upkeep (Multi-handed)", triggerUpkeepMultihanded) end --- triggers the "Upkeep" function of the calling player's playmat +-- triggers the "Upkeep" function of the calling player's playermat function triggerUpkeep(playerColor) if playerColor == "Black" then broadcastToColor("Triggering 'Upkeep (Multihanded)' instead", playerColor, "Yellow") triggerUpkeepMultihanded(playerColor) return end - local matColor = playmatApi.getMatColor(playerColor) - playmatApi.doUpkeepFromHotkey(matColor, playerColor) + local matColor = playermatApi.getMatColor(playerColor) + playermatApi.doUpkeepFromHotkey(matColor, playerColor) end --- triggers the "Upkeep" function of the calling player's playmat AND --- for all playmats that don't have a seated player, but an investigator card +-- triggers the "Upkeep" function of the calling player's playermat AND +-- for all playermats that don't have a seated player, but an investigator card function triggerUpkeepMultihanded(playerColor) if playerColor ~= "Black" then triggerUpkeep(playerColor) end local colors = Player.getAvailableColors() for _, handColor in ipairs(colors) do - local matColor = playmatApi.getMatColor(handColor) - if playmatApi.returnInvestigatorId(matColor) ~= "00000" and Player[handColor].seated == false then - playmatApi.doUpkeepFromHotkey(matColor, playerColor) + local matColor = playermatApi.getMatColor(handColor) + if playermatApi.returnInvestigatorId(matColor) ~= "00000" and Player[handColor].seated == false then + playermatApi.doUpkeepFromHotkey(matColor, playerColor) end end end @@ -69,11 +69,11 @@ function takeCardIntoThreatArea(playerColor, hoveredObject) return end - local matColor = playmatApi.getMatColor(playerColor) + local matColor = playermatApi.getMatColor(playerColor) local mat = guidReferenceApi.getObjectByOwnerAndType(matColor, "Playermat") -- do not continue if the threat area is already full - if playmatApi.getEncounterCardDrawPosition(matColor, false) == playmatApi.getEncounterCardDrawPosition(matColor, true) then + if playermatApi.getEncounterCardDrawPosition(matColor, false) == playermatApi.getEncounterCardDrawPosition(matColor, true) then broadcastToColor("Threat area is full.", playerColor, "Yellow") return end @@ -84,10 +84,10 @@ function takeCardIntoThreatArea(playerColor, hoveredObject) table.insert(moveTheseObjects, obj) end - -- find out if the original card is on the green or red playmats + -- find out if the original card is on the green or red playermats local originalMatColor = guidReferenceApi.getOwnerOfObject(hoveredObject) - -- determine modifiers for the playmats + -- determine modifiers for the playermats local modifierY = 0 if originalMatColor == "Red" then modifierY = 90 @@ -103,7 +103,7 @@ function takeCardIntoThreatArea(playerColor, hoveredObject) end -- move the main card - local pos = playmatApi.getEncounterCardDrawPosition(matColor, false) + local pos = playermatApi.getEncounterCardDrawPosition(matColor, false) hoveredObject.setPosition(pos) hoveredObject.setRotation(hoveredObject.getRotation() - Vector(0, 270 - mat.getRotation().y - modifierY, 0)) @@ -156,7 +156,7 @@ function performDiscard(playerColor, hoveredObject) end local discardForMatColor = getColorToDiscardFor(hoveredObject, playerColor) - playmatApi.discardListOfObjects(discardForMatColor, discardTheseObjects) + playermatApi.discardListOfObjects(discardForMatColor, discardTheseObjects) end -- discard the top card of hovered deck, calling discardObject function @@ -180,22 +180,22 @@ end -- helper function to get the player to trigger the discard function for function getColorToDiscardFor(hoveredObject, playerColor) local pos = hoveredObject.getPosition() - local closestMatColor = playmatApi.getMatColorByPosition(pos) + local closestMatColor = playermatApi.getMatColorByPosition(pos) - -- check if actually on the closest playmat + -- check if actually on the closest playermat local closestMat = guidReferenceApi.getObjectByOwnerAndType(closestMatColor, "Playermat") local bounds = closestMat.getBounds() - -- define the area "near" the playmat - local bufferAroundPlaymat = 2 - local areaNearPlaymat = {} - areaNearPlaymat.minX = bounds.center.x - bounds.size.x / 2 - bufferAroundPlaymat - areaNearPlaymat.maxX = bounds.center.x + bounds.size.x / 2 + bufferAroundPlaymat - areaNearPlaymat.minZ = bounds.center.z - bounds.size.z / 2 - bufferAroundPlaymat - areaNearPlaymat.maxZ = bounds.center.z + bounds.size.z / 2 + bufferAroundPlaymat + -- define the area "near" the playermat + local bufferAroundPlayermat = 2 + local areaNearPlayermat = {} + areaNearPlayermat.minX = bounds.center.x - bounds.size.x / 2 - bufferAroundPlayermat + areaNearPlayermat.maxX = bounds.center.x + bounds.size.x / 2 + bufferAroundPlayermat + areaNearPlayermat.minZ = bounds.center.z - bounds.size.z / 2 - bufferAroundPlayermat + areaNearPlayermat.maxZ = bounds.center.z + bounds.size.z / 2 + bufferAroundPlayermat -- discard to closest mat if near it - if inArea(pos, areaNearPlaymat) then + if inArea(pos, areaNearPlayermat) then return closestMatColor end @@ -208,7 +208,7 @@ function getColorToDiscardFor(hoveredObject, playerColor) end -- discard to triggering mat if previous conditions weren't met - return playmatApi.getMatColor(playerColor) + return playermatApi.getMatColor(playerColor) end -- moves the hovered card to the victory display @@ -286,7 +286,7 @@ function removeOneUse(playerColor, hoveredObject) broadcastToAll(playerName .. " removed a token: " .. tokenName, playerColor) local discardForMatColor = getColorToDiscardFor(hoveredObject, playerColor) - playmatApi.discardListOfObjects(discardForMatColor, { targetObject }) + playermatApi.discardListOfObjects(discardForMatColor, { targetObject }) end -- switches the triggering player to the next seat (clockwise) @@ -314,7 +314,7 @@ function switchSeat(playerColor, direction) end -- get used playermats - local usedColors = playmatApi.getUsedMatColors() + local usedColors = playermatApi.getUsedMatColors() table.sort(usedColors, sortByHandPosition) -- get current seat index @@ -407,7 +407,7 @@ function takeClueFromLocation(playerColor, hoveredObject) local playerName, matColor, pos if Player[playerColor] and Player[playerColor].seated then playerName = Player[playerColor].steam_name - matColor = playmatApi.getMatColor(playerColor) + matColor = playermatApi.getMatColor(playerColor) else playerName = playerColor matColor = playerColor @@ -415,12 +415,12 @@ function takeClueFromLocation(playerColor, hoveredObject) if clickableClues then pos = { x = 0.49, y = 2.66, z = 0.00 } - playmatApi.updateCounter(matColor, "ClickableClueCounter", _, 1) + playermatApi.updateCounter(matColor, "ClickableClueCounter", _, 1) else - pos = playmatApi.transformLocalPosition({ x = -1.12, y = 0.05, z = 0.7 }, matColor) + pos = playermatApi.transformLocalPosition({ x = -1.12, y = 0.05, z = 0.7 }, matColor) end - local rot = playmatApi.returnRotation(matColor) + local rot = playermatApi.returnRotation(matColor) -- check if found clue is a stack or single token if clue.getQuantity() > 1 then diff --git a/src/core/Global.ttslua b/src/core/Global.ttslua index 3bc19033..98200319 100644 --- a/src/core/Global.ttslua +++ b/src/core/Global.ttslua @@ -3,7 +3,7 @@ local guidReferenceApi = require("core/GUIDReferenceApi") local mythosAreaApi = require("core/MythosAreaApi") local navigationOverlayApi = require("core/NavigationOverlayApi") local playAreaApi = require("core/PlayAreaApi") -local playmatApi = require("playermat/PlaymatApi") +local playermatApi = require("playermat/PlayermatApi") local searchLib = require("util/SearchLib") local soundCubeApi = require("core/SoundCubeApi") local tokenArrangerApi = require("accessories/TokenArrangerApi") @@ -196,7 +196,7 @@ function onObjectEnterZone(zone, object) object.type == "Tile" and object.getMemo() and not object.getLock() then - local matcolor = playmatApi.getMatColorByPosition(object.getPosition()) + local matcolor = playermatApi.getMatColorByPosition(object.getPosition()) local trash = guidReferenceApi.getObjectByOwnerAndType(matcolor, "Trash") trash.putObject(object) elseif zone.type == "Hand" and object.hasTag("CardWithHelper") then @@ -219,10 +219,10 @@ function onObjectNumberTyped(hoveredObject, playerColor, number) if hoveredObject.type ~= "Deck" and hoveredObject.type ~= "Card" then return end -- check whether the hovered object is part of a players draw objects - for _, color in ipairs(playmatApi.getUsedMatColors()) do - local deckAreaObjects = playmatApi.getDeckAreaObjects(color) + for _, color in ipairs(playermatApi.getUsedMatColors()) do + local deckAreaObjects = playermatApi.getDeckAreaObjects(color) if deckAreaObjects.topCard == hoveredObject or deckAreaObjects.draw == hoveredObject then - playmatApi.drawCardsWithReshuffle(color, number) + playermatApi.drawCardsWithReshuffle(color, number) return true end end @@ -238,9 +238,9 @@ function onObjectNumberTyped(hoveredObject, playerColor, number) end end --- TTS event, used to redraw the playmat slot symbols after a small delay to account for the custom font loading +-- TTS event, used to redraw the playermat slot symbols after a small delay to account for the custom font loading function onPlayerConnect() - Wait.time(function() playmatApi.redrawSlotSymbols("All") end, 0.2) + Wait.time(function() playermatApi.redrawSlotSymbols("All") end, 0.2) end --------------------------------------------------------- @@ -381,7 +381,7 @@ function returnAndRedraw(_, tokenGUID) local returnedToken = getObjectFromGUID(tokenGUID) local tokenName = returnedToken.getName() local indexOfReturnedToken = getTokenIndex(returnedToken) - local matColor = playmatApi.getMatColorByPosition(returnedToken.getPosition()) + local matColor = playermatApi.getMatColorByPosition(returnedToken.getPosition()) local mat = guidReferenceApi.getObjectByOwnerAndType(matColor, "Playermat") local takeParameters = { @@ -461,7 +461,7 @@ function drawChaosToken(params) local matGUID = params.mat.getGUID() - -- return token(s) on other playmat first + -- return token(s) on other playermat first if chaosTokensLastMatGUID ~= nil and chaosTokensLastMatGUID ~= matGUID and #chaosTokens ~= 0 then returnChaosTokens() chaosTokensLastMatGUID = nil @@ -563,8 +563,8 @@ function handleStatTrackerClick(_, _, isRightClick) playerColor = "White" playerName = "Overall" else - local matColor = playmatApi.getMatColorByPosition(getObjectFromGUID(key).getPosition()) - playerColor = playmatApi.getPlayerColor(matColor) + local matColor = playermatApi.getMatColorByPosition(getObjectFromGUID(key).getPosition()) + playerColor = playermatApi.getPlayerColor(matColor) playerName = Player[playerColor].steam_name or playerColor local playerSquidCount = personalStats["Auto-fail"] or 0 @@ -1346,8 +1346,7 @@ function contentDownloadCallback(request, params) if pos then spawnTable.position = pos else - broadcastToAll( - "Please make space in the area below the tentacle stand in the upper middle of the table and try again.", "Red") + broadcastToAll("Please make space in the area below the tentacle stand in the upper middle of the table and try again.", "Red") return end end @@ -1498,9 +1497,10 @@ function playermatRemovalSelected(player, selectedIndex, id) if mat then -- confirmation dialog about deletion player.pingTable(mat.getPosition()) - player.showConfirmDialog( - "Do you really want to remove " .. matColor .. "'s playermat and related objects? This can't be reversed.", - function() removePlayermat(matColor) end) + player.showConfirmDialog("Do you really want to remove " .. matColor .. "'s playermat and related objects? This can't be reversed.", + function() + removePlayermat(matColor) + end) else -- info dialog that it is already deleted player.showInfoDialog(matColor .. "'s playermat has already been removed.") @@ -1517,7 +1517,7 @@ function removePlayermat(matColor) if not matObjects.Playermat then return end -- remove action tokens - local actionTokens = playmatApi.searchAroundPlaymat(matColor, "isUniversalToken") + local actionTokens = playermatApi.searchAroundPlayermat(matColor, "isUniversalToken") for _, obj in ipairs(actionTokens) do obj.destruct() end @@ -1557,19 +1557,24 @@ function applyOptionPanelChange(id, state) -- option: Snap tags if id == "useSnapTags" then - playmatApi.setLimitSnapsByType(state, "All") + playermatApi.setLimitSnapsByType(state, "All") -- option: Draw 1 button elseif id == "showDrawButton" then - playmatApi.showDrawButton(state, "All") + playermatApi.showDrawButton(state, "All") + + -- option: Use class texture + elseif id == "useClassTexture" then + playermatApi.useClassTexture(state, "All") -- option: Clickable clue counters elseif id == "useClueClickers" then - playmatApi.clickableClues(state, "All") + playermatApi.clickableClues(state, "All") -- update master clue counter local counter = guidReferenceApi.getObjectByOwnerAndType("Mythos", "MasterClueCounter") counter.setVar("useClickableCounters", state) + elseif id == "enableCardHelpers" then toggleCardHelpers(state) @@ -1616,7 +1621,7 @@ end ---@param helperName string Name of the helper object ---@param state boolean Contains the state of the option: true = spawn it, false = remove it function spawnOrRemoveHelperForPlayermats(helperName, state) - for color, data in pairs(playmatApi.getHelperSpawnData("All", helperName)) do + for color, data in pairs(playermatApi.getHelperSpawnData("All", helperName)) do spawnOrRemoveHelper(state, helperName, data.position, data.rotation, color) end end @@ -1709,6 +1714,7 @@ function onClick_defaultSettings() showHandHelper = false, showSearchAssistant = false, showTitleSplash = true, + useClassTexture = true, useClueClickers = false, useResourceCounters = "disabled", useSnapTags = true diff --git a/src/core/MasterClueCounter.ttslua b/src/core/MasterClueCounter.ttslua index ec2cc78a..ef189fe1 100644 --- a/src/core/MasterClueCounter.ttslua +++ b/src/core/MasterClueCounter.ttslua @@ -1,4 +1,4 @@ -local playmatApi = require("playermat/PlaymatApi") +local playermatApi = require("playermat/PlayermatApi") -- variables are intentionally global to be accessible count = 0 @@ -31,12 +31,12 @@ end -- removes all player clues by calling the respective function from the counting bowls / clickers function removeAllPlayerClues() printToAll(count .. " clue(s) from playermats removed.", "White") - playmatApi.removeClues("All") + playermatApi.removeClues("All") self.editButton({ index = 0, label = "0" }) end -- gets the counted values from the counting bowls / clickers and sums them up function sumClues() - count = playmatApi.getClueCount(useClickableCounters, "All") + count = playermatApi.getClueCount(useClickableCounters, "All") self.editButton({ index = 0, label = tostring(count) }) end diff --git a/src/core/MythosArea.ttslua b/src/core/MythosArea.ttslua index 4b01d41d..9ce728d3 100644 --- a/src/core/MythosArea.ttslua +++ b/src/core/MythosArea.ttslua @@ -1,7 +1,7 @@ local deckLib = require("util/DeckLib") local guidReferenceApi = require("core/GUIDReferenceApi") local playAreaApi = require("core/PlayAreaApi") -local playmatApi = require("playermat/PlaymatApi") +local playermatApi = require("playermat/PlayermatApi") local searchLib = require("util/SearchLib") local tokenArrangerApi = require("accessories/TokenArrangerApi") local tokenChecker = require("core/token/TokenChecker") @@ -22,7 +22,14 @@ local ENCOUNTER_DISCARD_POSITION = { x = -3.85, y = 1, z = 10.38 } local isReshuffling = false local collisionEnabled = false local currentScenario, useFrontData, tokenData -local TRASH, DATA_HELPER + +function onSave() + return JSON.encode({ + currentScenario = currentScenario, + useFrontData = useFrontData, + tokenData = tokenData + }) +end function onLoad(savedData) if savedData and savedData ~= "" then @@ -31,20 +38,9 @@ function onLoad(savedData) useFrontData = loadedState.useFrontData or true tokenData = loadedState.tokenData or {} end - TRASH = guidReferenceApi.getObjectByOwnerAndType("Mythos", "Trash") - DATA_HELPER = guidReferenceApi.getObjectByOwnerAndType("Mythos", "DataHelper") - Wait.time(function() collisionEnabled = true end, 0.1) end -function onSave() - return JSON.encode({ - currentScenario = currentScenario, - useFrontData = useFrontData, - tokenData = tokenData - }) -end - --------------------------------------------------------- -- collison and container event handling --------------------------------------------------------- @@ -179,9 +175,10 @@ function drawEncounterCard(params) end end --- draw the provided card to the requesting playmat +-- draw the provided card to the requesting playermat function actualEncounterCardDraw(card, params) local metadata = JSON.decode(card.getGMNotes()) or {} + local DATA_HELPER = guidReferenceApi.getObjectByOwnerAndType("Mythos", "DataHelper") -- draw hidden cards facedown local faceUpRotation = 0 @@ -189,7 +186,7 @@ function actualEncounterCardDraw(card, params) faceUpRotation = 180 end - local rot = playmatApi.returnRotation(params.matColor):setAt("z", faceUpRotation) + local rot = playermatApi.returnRotation(params.matColor):setAt("z", faceUpRotation) deckLib.placeOrMergeIntoDeck(card, params.position, rot) end @@ -249,6 +246,7 @@ end -- removes tokens from the provided card/deck function removeTokensFromObject(object) + local TRASH = guidReferenceApi.getObjectByOwnerAndType("Mythos", "Trash") for _, obj in ipairs(searchLib.onObject(object)) do if obj.getGUID() ~= "4ee1f2" and -- table obj ~= self and diff --git a/src/core/NavigationOverlayHandler.ttslua b/src/core/NavigationOverlayHandler.ttslua index 66fe917b..ad8f37d4 100644 --- a/src/core/NavigationOverlayHandler.ttslua +++ b/src/core/NavigationOverlayHandler.ttslua @@ -1,4 +1,4 @@ -local playmatApi = require("playermat/PlaymatApi") +local playermatApi = require("playermat/PlayermatApi") fullButtonData = { { id = "1", width = "84", height = "33", offset = "1 2" }, -- 1. Act/Agenda @@ -44,10 +44,10 @@ playButtonData = { cameraData = { { position = { -1.6, 1.55, 0 }, distance = 18 }, -- 1. Act/Agenda { position = { -28, 1.55, 0 }, distance = -1 }, -- 2. Map - { position = { -31.6, 1.55, 26.4 }, distance = -1 }, -- 3. Green playmat - { position = { -55, 1.55, 12.05 }, distance = -1 }, -- 4. White playmat - { position = { -55, 1.55, -11.48 }, distance = -1 }, -- 5. Orange playmat - { position = { -31.6, 1.55, -26.4 }, distance = -1 }, -- 6. Red playmat + { position = { -31.6, 1.55, 26.4 }, distance = -1 }, -- 3. Green playermat + { position = { -55, 1.55, 12.05 }, distance = -1 }, -- 4. White playermat + { position = { -55, 1.55, -11.48 }, distance = -1 }, -- 5. Orange playermat + { position = { -31.6, 1.55, -26.4 }, distance = -1 }, -- 6. Red playermat { position = { -3, 1.55, 30 }, distance = 16 }, -- 7. Victory / SetAside { position = { -3, 1.55, -26.76 }, distance = 16 }, -- 8. Guide { position = { -11.83, 1.55, 0 }, distance = 10 }, -- 9. Player count @@ -89,13 +89,9 @@ function onLoad(savedData) pitch = loadedData.pitch distance = loadedData.distance else - local allColors = Player.getColors() - - for _, color in ipairs(allColors) do - -- default state for claims + -- initialize tables with defaults + for _, color in ipairs(Player.getColors()) do claims[color] = {} - - -- default state for visibility visibility[color] = { full = false, play = false } end end @@ -338,19 +334,19 @@ function loadCamera(player, camera) end -- swap to that color if it isn't claimed by someone else and it's currently unoccopied - if #getSeatedPlayers() == 1 or (not isClaimed and isPlaymatAvailable(matColor)) then - local newPlayerColor = playmatApi.getPlayerColor(matColor) + if #getSeatedPlayers() == 1 or (not isClaimed and isPlayermatAvailable(matColor)) then + local newPlayerColor = playermatApi.getPlayerColor(matColor) copyVisibility({ startColor = player.color, targetColor = newPlayerColor }) player.changeColor(newPlayerColor) player = Player[newPlayerColor] end - -- search on the playmat for objects - local bounds = getDynamicViewBounds(playmatApi.searchAroundPlaymat(matColor)) + -- search on the playermat for objects + local bounds = getDynamicViewBounds(playermatApi.searchAroundPlayermat(matColor)) lookHere = { position = { bounds.middleX, 0, bounds.middleZ }, - yaw = playmatApi.returnRotation(matColor).y + 180, + yaw = playermatApi.returnRotation(matColor).y + 180, distance = 0.42 * math.max(bounds.diffX, bounds.diffZ) + 7 } end @@ -371,9 +367,9 @@ function loadCamera(player, camera) Wait.frames(function() player.lookAt(lookHere) end, 2) end --- helper function to check if a playmat is available for a color swap -function isPlaymatAvailable(matColor) - local newPlayerColor = playmatApi.getPlayerColor(matColor) +-- helper function to check if a playermat is available for a color swap +function isPlayermatAvailable(matColor) + local newPlayerColor = playermatApi.getPlayerColor(matColor) for _, color in ipairs(getSeatedPlayers()) do if color == newPlayerColor then return false diff --git a/src/core/PlayArea.ttslua b/src/core/PlayArea.ttslua index 92f265ca..22447b3f 100644 --- a/src/core/PlayArea.ttslua +++ b/src/core/PlayArea.ttslua @@ -133,7 +133,7 @@ function onObjectPickUp(_, object) local metadata = JSON.decode(object.getGMNotes()) or {} if metadata.type == "Location" then -- onCollisionExit sometimes comes 1 frame after onObjectPickUp (rather than before it or in - -- the same frame). This causes a mismatch in the data between dragging the on-table, and + -- the same frame). This causes a mismatch in the data between dragging the on-table, and -- that one frame draws connectors on the card which then show up as shadows for snap points. -- Waiting ensures we always do thing in the expected Exit->PickUp order Wait.frames(function() @@ -240,7 +240,7 @@ end ---@param card tts__Object Card to (maybe) stop tracking function maybeUntrackLocation(card) -- Locked objects no longer collide (hence triggering an exit event) but are still in the play - -- area. If the object is now locked, don't remove it. + -- area. If the object is now locked, don't remove it. if locations[card.getGUID()] ~= nil and not card.locked then locations[card.getGUID()] = nil rebuildConnectionList() @@ -415,7 +415,7 @@ end ---@param target tts__Object Target card object to connect ---@param vectorOwner tts__Object The object which these lines will be set to. Used for relative --- positioning and scaling, as well as highlighting connections during a drag operation ----@param lines table List of vector line elements. Mutable, will be updated to add this connector +---@param lines table List of vector line elements. Mutable, will be updated to add this connector function addOneWayVector(origin, target, vectorOwner, lines) -- Start with the BiDi then add the arrow lines to it addBidirectionalVector(origin, target, vectorOwner, lines) @@ -445,9 +445,9 @@ end -- Draws an arrowhead at the given position. ---@param arrowheadPos tts__Vector Centerpoint of the arrowhead to draw (NOT the tip of the arrow) ---@param originPos tts__Vector Origin point of the connection, used to position the arrow arms ----@param vectorOwner tts__Object The object which these lines will be set to. Used for relative +---@param vectorOwner tts__Object The object which these lines will be set to. Used for relative --- positioning and scaling, as well as highlighting connections during a drag operation ----@param lines table List of vector line elements. Mutable, will be updated to add this arrow +---@param lines table List of vector line elements. Mutable, will be updated to add this arrow function addArrowLines(arrowheadPos, originPos, vectorOwner, lines) local arrowArm1 = Vector(arrowheadPos):moveTowards(originPos, ARROW_ARM_LENGTH):sub(arrowheadPos):rotateOver("y", -1 * ARROW_ANGLE):add(arrowheadPos) local arrowArm2 = Vector(arrowheadPos):moveTowards(originPos, ARROW_ARM_LENGTH):sub(arrowheadPos):rotateOver("y", ARROW_ANGLE):add(arrowheadPos) @@ -462,7 +462,7 @@ function addArrowLines(arrowheadPos, originPos, vectorOwner, lines) }) end --- count victory points on locations in play area +-- Count victory points from locations in play area ---@param highlightOff boolean True if highlighting should be enabled ---@return. Returns the total amount of VP found in the play area function countVP(highlightOff) @@ -488,14 +488,15 @@ function countVP(highlightOff) return totalVP end --- checks if a card has clues on it, returns true if clues are on it +-- Checks if a card has clues on it ---@param card tts__Object Card to check for clues +---@return boolean hasClues True if card has clues on it function cardHasClues(card) local searchResult = searchLib.onObject(card, "isClue") return #searchResult > 0 end --- highlights all locations in the play area without metadata +-- Highlights all locations in the play area without metadata ---@param state boolean True if highlighting should be enabled function highlightMissingData(state) for i, obj in pairs(missingData) do @@ -549,7 +550,7 @@ function shiftContents(playerColor, direction) Wait.time(drawBaseConnections, 0.1) end --- sets the image of the playarea +-- Sets the image of the playarea ---@param newURL string URL for the new surface image function updateSurface(newURL) local customInfo = self.getCustomObject() @@ -569,6 +570,7 @@ function updateSurface(newURL) guid = customDataHelper.getGUID() end + self.script_state = onSave() self.reload() if guid ~= nil then @@ -646,7 +648,7 @@ function round(num, numDecimalPlaces) return math.floor(num * mult + 0.5) / mult end --- rebuilds local snap points (could be useful in the future again) +-- Rebuilds local snap points (could be useful in the future again) function buildSnaps() local upperleft = { x = 1.53, z = -1.09 } local lowerright = { x = -1.53, z = 1.55 } diff --git a/src/core/PlayAreaApi.ttslua b/src/core/PlayAreaApi.ttslua index 72096f1d..37116cec 100644 --- a/src/core/PlayAreaApi.ttslua +++ b/src/core/PlayAreaApi.ttslua @@ -10,13 +10,13 @@ do return guidReferenceApi.getObjectByOwnerAndType("Mythos", "InvestigatorCounter") end - -- Returns the current value of the investigator counter from the playmat + -- Returns the current value of the investigator counter from the playermat ---@return number: Number of investigators currently set on the counter PlayAreaApi.getInvestigatorCount = function() return getInvestigatorCounter().getVar("val") end - -- Updates the current value of the investigator counter from the playmat + -- Updates the current value of the investigator counter from the playermat ---@param count number Number of investigators to set on the counter PlayAreaApi.setInvestigatorCount = function(count) getInvestigatorCounter().call("updateVal", count) @@ -57,7 +57,7 @@ do getPlayArea().call("onScenarioChanged", scenarioName) end - -- Sets this playmat's snap points to limit snapping to locations or not. + -- Sets this playermat's snap points to limit snapping to locations or not. -- If matchTypes is false, snap points will be reset to snap all cards. ---@param matchCardTypes boolean Whether snap points should only snap for the matching card types PlayAreaApi.setLimitSnapsByType = function(matchCardTypes) diff --git a/src/core/PlayAreaSelector.ttslua b/src/core/PlayAreaSelector.ttslua index e5431e1a..0824dde9 100644 --- a/src/core/PlayAreaSelector.ttslua +++ b/src/core/PlayAreaSelector.ttslua @@ -3,7 +3,12 @@ local optionPanelApi = require("core/OptionPanelApi") local playAreaApi = require("core/PlayAreaApi") local typeIndex, selectionIndex, plainNameCache -function onSave() return JSON.encode({ typeIndex = typeIndex, selectionIndex = selectionIndex }) end +function onSave() + return JSON.encode({ + typeIndex = typeIndex, + selectionIndex = selectionIndex + }) +end function onLoad(savedData) if savedData and savedData ~= "" then @@ -192,7 +197,7 @@ end function getPlainName(str) -- remove prefix type 1 str = str:gsub("%w+%-%w%s%-%s", "") -- matches "II-B - Thousand Shapes of Horror 1" - + -- remove prefix type 2 str = str:gsub("%w+%-%w%s", "") -- matches "59-Z Congress of Keys 1" diff --git a/src/core/token/TokenManager.ttslua b/src/core/token/TokenManager.ttslua index 553400c8..899f9f7b 100644 --- a/src/core/token/TokenManager.ttslua +++ b/src/core/token/TokenManager.ttslua @@ -2,7 +2,7 @@ do local guidReferenceApi = require("core/GUIDReferenceApi") local optionPanelApi = require("core/OptionPanelApi") local playAreaApi = require("core/PlayAreaApi") - local playmatApi = require("playermat/PlaymatApi") + local playermatApi = require("playermat/PlayermatApi") local searchLib = require("util/SearchLib") local tokenSpawnTrackerApi = require("core/token/TokenSpawnTrackerApi") @@ -133,13 +133,13 @@ do local TokenManager = {} local internal = {} - -- Spawns tokens for the card. This function is built to just throw a card at it and let it do - -- the work once a card has hit an area where it might spawn tokens. It will check to see if + -- Spawns tokens for the card. This function is built to just throw a card at it and let it do + -- the work once a card has hit an area where it might spawn tokens. It will check to see if -- the card has already spawned, find appropriate data from either the uses metadata or the Data -- Helper, and spawn the tokens. ---@param card tts__Object Card to maybe spawn tokens for ---@param extraUses table A table of = which will modify the number of tokens - --- spawned for that type. e.g. Akachi's playmat should pass "Charge"=1 + --- spawned for that type. e.g. Akachi's playermat should pass "Charge"=1 TokenManager.spawnForCard = function(card, extraUses) if tokenSpawnTrackerApi.hasSpawnedTokens(card.getGUID()) then return @@ -155,10 +155,10 @@ do -- Spawns a set of tokens on the given card. ---@param card tts__Object Card to spawn tokens on ---@param tokenType string Type of token to spawn (template needs to be in source bag) - ---@param tokenCount number How many tokens to spawn. For damage or horror this value will be set to the + ---@param tokenCount number How many tokens to spawn. For damage or horror this value will be set to the -- spawned state object rather than spawning multiple tokens ---@param shiftDown? number An offset for the z-value of this group of tokens - ---@param subType? string Subtype of token to spawn. This will only differ from the tokenName for resource tokens + ---@param subType? string Subtype of token to spawn. This will only differ from the tokenName for resource tokens TokenManager.spawnTokenGroup = function(card, tokenType, tokenCount, shiftDown, subType) local optionPanel = optionPanelApi.getOptions() @@ -244,8 +244,8 @@ do if tokenType == "resource" and stateID ~= nil and stateID ~= 1 then callback = function(spawned) spawned.setState(stateID) end elseif tokenType == "universalActionAbility" then - local matColor = playmatApi.getMatColorByPosition(card.getPosition()) - local class = playmatApi.returnInvestigatorClass(matColor) + local matColor = playermatApi.getMatColorByPosition(card.getPosition()) + local class = playermatApi.returnInvestigatorClass(matColor) callback = function(spawned) spawned.call("updateClassAndSymbol", { class = class, symbol = subType or class }) end end @@ -294,7 +294,7 @@ do -- Checks a card for metadata to maybe replenish it ---@param card tts__Object Card object to be replenished ---@param uses table The already decoded metadata.uses (to avoid decoding again) - ---@param mat tts__Object The playmat the card is placed on (for rotation and casting) + ---@param mat tts__Object The playermat the card is placed on (for rotation and casting) TokenManager.maybeReplenishCard = function(card, uses, mat) -- TODO: support for cards with multiple uses AND replenish (as of yet, no official card needs that) if uses[1].count and uses[1].replenish then @@ -302,7 +302,7 @@ do end end - -- Delegate function to the token spawn tracker. Exists to avoid circular dependencies in some + -- Delegate function to the token spawn tracker. Exists to avoid circular dependencies in some -- callers. ---@param card tts__Object Card object to reset the tokens for TokenManager.resetTokensSpawned = function(card) @@ -347,7 +347,7 @@ do end end - -- Copies the data from the DataHelper. Will only happen once. + -- Copies the data from the DataHelper. Will only happen once. internal.initDataHelperData = function() if playerCardData ~= nil then return @@ -357,11 +357,11 @@ do locationData = dataHelper.getTable('LOCATIONS_DATA') end - -- Spawn tokens for a card based on the uses metadata. This will consider the face up/down state + -- Spawn tokens for a card based on the uses metadata. This will consider the face up/down state -- of the card for both locations and standard cards. ---@param card tts__Object Card to maybe spawn tokens for ---@param extraUses table A table of = which will modify the number of tokens - --- spawned for that type. e.g. Akachi's playmat should pass "Charge"=1 + --- spawned for that type. e.g. Akachi's playermat should pass "Charge"=1 internal.spawnTokensFromUses = function(card, extraUses) local uses = internal.getUses(card) if uses == nil then return end @@ -380,7 +380,7 @@ do tokenSpawnTrackerApi.markTokensSpawned(card.getGUID()) end - -- Spawn tokens for a card based on the data helper data. This will consider the face up/down state + -- Spawn tokens for a card based on the data helper data. This will consider the face up/down state -- of the card for both locations and standard cards. ---@param card tts__Object Card to maybe spawn tokens for internal.spawnTokensFromDataHelper = function(card) @@ -397,7 +397,7 @@ do -- Spawn tokens for a player card using data retrieved from the Data Helper. ---@param card tts__Object Card to maybe spawn tokens for - ---@param playerData table Player card data structure retrieved from the DataHelper. Should be + ---@param playerData table Player card data structure retrieved from the DataHelper. Should be -- the right data for this card. internal.spawnPlayerCardTokensFromDataHelper = function(card, playerData) local token = playerData.tokenType @@ -408,7 +408,7 @@ do -- Spawn tokens for a location using data retrieved from the Data Helper. ---@param card tts__Object Card to maybe spawn tokens for - ---@param locationData table Location data structure retrieved from the DataHelper. Should be + ---@param locationData table Location data structure retrieved from the DataHelper. Should be -- the right data for this card. internal.spawnLocationTokensFromDataHelper = function(card, locationData) local clueCount = internal.getClueCountFromData(card, locationData) @@ -481,7 +481,7 @@ do ---@param card tts__Object Card object to be replenished ---@param uses table The already decoded metadata.uses (to avoid decoding again) - ---@param mat tts__Object The playmat the card is placed on (for rotation and casting) + ---@param mat tts__Object The playermat the card is placed on (for rotation and casting) internal.replenishTokens = function(card, uses, mat) local cardPos = card.getPosition() diff --git a/src/playercards/CardSearch.ttslua b/src/playercards/CardSearch.ttslua index b3cb5228..f5143f2e 100644 --- a/src/playercards/CardSearch.ttslua +++ b/src/playercards/CardSearch.ttslua @@ -23,7 +23,9 @@ inputParameters.scale = { 0.1, 1, 0.1 } inputParameters.color = { 0.9, 0.7, 0.5 } inputParameters.font_color = { 0, 0, 0 } -function onSave() return JSON.encode({ spawnAll, searchExact, inputParameters.value }) end +function onSave() + return JSON.encode({ spawnAll, searchExact, inputParameters.value }) +end function onLoad(savedData) local loadedData = JSON.decode(savedData) diff --git a/src/playercards/CardsThatSealTokens.ttslua b/src/playercards/CardsThatSealTokens.ttslua index 3c43156a..009c4933 100644 --- a/src/playercards/CardsThatSealTokens.ttslua +++ b/src/playercards/CardsThatSealTokens.ttslua @@ -76,7 +76,7 @@ Thus it should be implemented like this: local blessCurseManagerApi = require("chaosbag/BlessCurseManagerApi") local chaosBagApi = require("chaosbag/ChaosBagApi") local guidReferenceApi = require("core/GUIDReferenceApi") -local playmatApi = require("playermat/PlaymatApi") +local playermatApi = require("playermat/PlayermatApi") local tokenArrangerApi = require("accessories/TokenArrangerApi") local sealedTokens = {} @@ -280,7 +280,7 @@ function resolveSealed() broadcastToAll("No tokens sealed.", "Red") return end - local closestMatColor = playmatApi.getMatColorByPosition(self.getPosition()) + local closestMatColor = playermatApi.getMatColorByPosition(self.getPosition()) local mat = guidReferenceApi.getObjectByOwnerAndType(closestMatColor, "Playermat") local guidToBeResolved = table.remove(sealedTokens) chaosBagApi.drawChaosToken(mat, true, _, guidToBeResolved) diff --git a/src/playercards/cards/BookofLivingMyths.ttslua b/src/playercards/cards/BookofLivingMyths.ttslua index e018a657..7f7f116b 100644 --- a/src/playercards/cards/BookofLivingMyths.ttslua +++ b/src/playercards/cards/BookofLivingMyths.ttslua @@ -1,7 +1,7 @@ require("playercards/CardsWithHelper") local chaosBagApi = require("chaosbag/ChaosBagApi") local guidReferenceApi = require("core/GUIDReferenceApi") -local playmatApi = require("playermat/PlaymatApi") +local playermatApi = require("playermat/PlayermatApi") local isHelperEnabled = false @@ -37,9 +37,9 @@ end function resolveToken(player, _, tokenType) local matColor if player.color == "Black" then - matColor = playmatApi.getMatColorByPosition(self.getPosition()) + matColor = playermatApi.getMatColorByPosition(self.getPosition()) else - matColor = playmatApi.getMatColor(player.color) + matColor = playermatApi.getMatColor(player.color) end local mat = guidReferenceApi.getObjectByOwnerAndType(matColor, "Playermat") diff --git a/src/playercards/cards/EmpiricalHypothesis.ttslua b/src/playercards/cards/EmpiricalHypothesis.ttslua index 77c46979..21f1f986 100644 --- a/src/playercards/cards/EmpiricalHypothesis.ttslua +++ b/src/playercards/cards/EmpiricalHypothesis.ttslua @@ -1,5 +1,5 @@ require("playercards/CardsWithHelper") -local playmatApi = require("playermat/PlaymatApi") +local playermatApi = require("playermat/PlayermatApi") -- common button parameters local buttonParameters = {} @@ -109,9 +109,9 @@ function createButtons() end function findUpgradeSheet() - local matColor = playmatApi.getMatColorByPosition(self.getPosition()) - local result = playmatApi.searchAroundPlaymat(matColor, "isCard") - for _, card in ipairs(result) do + local matColor = playermatApi.getMatColorByPosition(self.getPosition()) + local result = playermatApi.searchAroundPlaymat(matColor, "isCard") + for j, card in ipairs(result) do local metadata = JSON.decode(card.getGMNotes()) or {} if metadata.id == "09041-c" then return card diff --git a/src/playercards/cards/FamilyInheritance.ttslua b/src/playercards/cards/FamilyInheritance.ttslua index b3222057..19ea08cc 100644 --- a/src/playercards/cards/FamilyInheritance.ttslua +++ b/src/playercards/cards/FamilyInheritance.ttslua @@ -1,4 +1,4 @@ -local playmatApi = require("playermat/PlaymatApi") +local playermatApi = require("playermat/PlayermatApi") local searchLib = require("util/SearchLib") local tokenManager = require("core/token/TokenManager") @@ -46,8 +46,8 @@ end function takeAll(playerColor) searchSelf() - local matColor = playmatApi.getMatColorByPosition(self.getPosition()) - playmatApi.updateCounter(matColor, "ResourceCounter", _, foundTokens) + local matColor = playermatApi.getMatColorByPosition(self.getPosition()) + playermatApi.updateCounter(matColor, "ResourceCounter", _, foundTokens) if clickableResourceCounter then clickableResourceCounter.call("updateVal", 0) diff --git a/src/playercards/cards/ScrollofSecrets.ttslua b/src/playercards/cards/ScrollofSecrets.ttslua index 964912bd..309e0605 100644 --- a/src/playercards/cards/ScrollofSecrets.ttslua +++ b/src/playercards/cards/ScrollofSecrets.ttslua @@ -1,6 +1,6 @@ -- this script is shared between the lvl 0 and lvl 3 versions of Scroll of Secrets local mythosAreaApi = require("core/MythosAreaApi") -local playmatApi = require("playermat/PlaymatApi") +local playermatApi = require("playermat/PlayermatApi") -- get class via metadata and create context menu accordingly function onLoad() @@ -30,8 +30,8 @@ function contextFunc(playerColor, amount) -- check for players with a deck and only display them as option for _, color in ipairs(Player.getAvailableColors()) do - local matColor = playmatApi.getMatColor(color) - local deckAreaObjects = playmatApi.getDeckAreaObjects(matColor) + local matColor = playermatApi.getMatColor(color) + local deckAreaObjects = playermatApi.getDeckAreaObjects(matColor) if deckAreaObjects.draw or deckAreaObjects.topCard then table.insert(options, color) @@ -52,8 +52,8 @@ function drawCardsFromBottom(playerColor, owner, amount) if owner == "Encounter Deck" then deck = mythosAreaApi.getEncounterDeck() else - local matColor = playmatApi.getMatColor(owner) - deckAreaObjects = playmatApi.getDeckAreaObjects(matColor) + local matColor = playermatApi.getMatColor(owner) + deckAreaObjects = playermatApi.getDeckAreaObjects(matColor) deck = deckAreaObjects.draw end diff --git a/src/playercards/cards/ShortSupply.ttslua b/src/playercards/cards/ShortSupply.ttslua index 877dc5d6..8074211b 100644 --- a/src/playercards/cards/ShortSupply.ttslua +++ b/src/playercards/cards/ShortSupply.ttslua @@ -1,4 +1,4 @@ -local playmatApi = require("playermat/PlaymatApi") +local playermatApi = require("playermat/PlayermatApi") function onLoad() self.addContextMenuItem("Discard 10 cards", shortSupply) @@ -6,12 +6,12 @@ end -- called by context menu entry function shortSupply(color) - local matColor = playmatApi.getMatColorByPosition(self.getPosition()) + local matColor = playermatApi.getMatColorByPosition(self.getPosition()) -- get draw deck and discard position - local deckAreaObjects = playmatApi.getDeckAreaObjects(matColor) + local deckAreaObjects = playermatApi.getDeckAreaObjects(matColor) local drawDeck = deckAreaObjects.draw - local discardPos = playmatApi.getDiscardPosition(matColor) + local discardPos = playermatApi.getDiscardPosition(matColor) -- error handling if discardPos == nil then diff --git a/src/playercards/cards/Tekeli-li.ttslua b/src/playercards/cards/Tekeli-li.ttslua index 2ee3ab78..acf90fae 100644 --- a/src/playercards/cards/Tekeli-li.ttslua +++ b/src/playercards/cards/Tekeli-li.ttslua @@ -1,5 +1,5 @@ local deckLib = require("util/DeckLib") -local playmatApi = require("playermat/PlaymatApi") +local playermatApi = require("playermat/PlayermatApi") function onLoad() self.addContextMenuItem("Return this card", returnSelf) @@ -18,9 +18,9 @@ end -- places this card below the deck of the player that triggered it function placeBelowDeck(playerColor) - local matColor = playmatApi.getMatColor(playerColor) - local deckPos = playmatApi.getDrawPosition(matColor) - local deckRot = playmatApi.returnRotation(matColor) + local matColor = playermatApi.getMatColor(playerColor) + local deckPos = playermatApi.getDrawPosition(matColor) + local deckRot = playermatApi.returnRotation(matColor) deckRot = deckRot:setAt("z", 180) deckLib.placeOrMergeIntoDeck(self, Vector(deckPos), deckRot, true) end diff --git a/src/playercards/cards/WellConnected.ttslua b/src/playercards/cards/WellConnected.ttslua index f93ec0d6..c90ca5e4 100644 --- a/src/playercards/cards/WellConnected.ttslua +++ b/src/playercards/cards/WellConnected.ttslua @@ -1,5 +1,5 @@ require("playercards/CardsWithHelper") -local playmatApi = require("playermat/PlaymatApi") +local playermatApi = require("playermat/PlayermatApi") local buttonParameters = { click_function = "shutOff", @@ -46,8 +46,8 @@ function shutOff() end function updateButton() - local matColor = playmatApi.getMatColorByPosition(self.getPosition()) - local resources = playmatApi.getCounterValue(matColor, "ResourceCounter") + local matColor = playermatApi.getMatColorByPosition(self.getPosition()) + local resources = playermatApi.getCounterValue(matColor, "ResourceCounter") local count = tostring(math.floor(resources / modValue)) self.editButton({ index = 0, label = count }) end diff --git a/src/playercards/customizable/UpgradeSheetLibrary.ttslua b/src/playercards/customizable/UpgradeSheetLibrary.ttslua index 07e1647a..4941b22b 100644 --- a/src/playercards/customizable/UpgradeSheetLibrary.ttslua +++ b/src/playercards/customizable/UpgradeSheetLibrary.ttslua @@ -19,7 +19,7 @@ -- selectedUpgrades holds the state of checkboxes and text input, each element being: -- selectedUpgrades[row] = { xp = #, text = "" } -local playmatApi = require("playermat/PlaymatApi") +local playermatApi = require("playermat/PlayermatApi") -- Y position for UI elements. Visibility of checkboxes moves the checkbox inside the card object -- when not selected. @@ -230,7 +230,7 @@ function clickCheckbox(row, col) selectedUpgrades[row].xp = col end updateCheckboxes(row) - playmatApi.syncAllCustomizableCards() + playermatApi.syncAllCustomizableCards() end -- Updates saved value for given text box when it loses focus diff --git a/src/playermat/ClueCounter.ttslua b/src/playermat/ClueCounter.ttslua index 2e0539e8..a08e0a4b 100644 --- a/src/playermat/ClueCounter.ttslua +++ b/src/playermat/ClueCounter.ttslua @@ -1,10 +1,10 @@ local guidReferenceApi = require("core/GUIDReferenceApi") -local playmatApi = require("playermat/PlaymatApi") +local playermatApi = require("playermat/PlayermatApi") local searchLib = require("util/SearchLib") exposedValue = 0 -local playmat +local playermat local searchParam = {} function onLoad() @@ -19,14 +19,14 @@ function onLoad() font_size = 2000 }) - -- get closest playmat - local matColor = playmatApi.getMatColorByPosition(self.getPosition()) - playmat = guidReferenceApi.getObjectByOwnerAndType(matColor, "Playermat") + -- get closest playermat + local matColor = playermatApi.getMatColorByPosition(self.getPosition()) + playermat = guidReferenceApi.getObjectByOwnerAndType(matColor, "Playermat") -- get search parameters (threat area excluded) - local localPos = playmat.positionToLocal(playmat.getPosition()) - searchParam.pos = playmat.positionToWorld(localPos + Vector(0, 0, 0.4)) - searchParam.rot = playmat.getRotation() + Vector(0, 90, 0) + local localPos = playermat.positionToLocal(playermat.getPosition()) + searchParam.pos = playermat.positionToWorld(localPos + Vector(0, 0, 0.4)) + searchParam.rot = playermat.getRotation() + Vector(0, 90, 0) searchParam.size = Vector(8, 1, 27) searchParam.filter = "isClue" @@ -34,7 +34,7 @@ function onLoad() Wait.time(countItems, 1.5, -1) end --- activated once per second, counts clues on the playmat +-- activated once per second, counts clues on the playermat function countItems() local totalValue = 0 for _, item in ipairs(getClues()) do diff --git a/src/playermat/Playmat.ttslua b/src/playermat/Playermat.ttslua similarity index 92% rename from src/playermat/Playmat.ttslua rename to src/playermat/Playermat.ttslua index 7bc447f0..f4208b93 100644 --- a/src/playermat/Playmat.ttslua +++ b/src/playermat/Playermat.ttslua @@ -46,7 +46,7 @@ local DRAWN_ENCOUNTER_POSITION = { x = 1.365, y = 0.5, z = -0.625 } -- global position of encounter discard pile local ENCOUNTER_DISCARD_POSITION = { x = -3.85, y = 1.5, z = 10.38 } --- used for the buttons on the right side of the playmat +-- used for the buttons on the right side of the playermat -- starts off with the data for the "Upkeep" button and will then be changed local buttonParameters = { label = "Upkeep", @@ -60,6 +60,16 @@ local buttonParameters = { font_size = 180 } +-- table of texture URLs +local nameToTexture = { + Guardian = "http://cloud-3.steamusercontent.com/ugc/2444972799638881117/169F4520A94FB186B54E0F2BF4BAC809844C923E/", + Mystic = "http://cloud-3.steamusercontent.com/ugc/2444972799638880413/B59966123EA41649EDCBD614167E590C8C105582/", + Neutral = "http://cloud-3.steamusercontent.com/ugc/2462982115659543571/5D778EA4BC682DAE97E8F59A991BCF8CB3979B04/", + Rogue = "http://cloud-3.steamusercontent.com/ugc/2444972799638880905/CFC02BF5A6140B9B4B92312AD6DC74D8DD61180B/", + Seeker = "http://cloud-3.steamusercontent.com/ugc/2444972799638881117/169F4520A94FB186B54E0F2BF4BAC809844C923E/", + Survivor = "http://cloud-3.steamusercontent.com/ugc/2444972799638880687/EEDF8F8BC3266069FECB09775845BE2501310C17/" +} + -- translation table for slot names to characters for special font local slotNameToChar = { ["any"] = "", @@ -86,12 +96,11 @@ local defaultSlotData = { -- global variables for access activeInvestigatorClass = "Neutral" activeInvestigatorId = "00000" - -local isDrawButtonVisible = false - --- global variable to report "Dream-Enhancing Serum" status hasDES = false +local isClassTextureEnabled = true +local isDrawButtonVisible = false + -- table of type-object reference pairs of all owned objects local ownedObjects = {} local matColor = self.getMemo() @@ -100,6 +109,7 @@ function onSave() return JSON.encode({ activeInvestigatorClass = activeInvestigatorClass, activeInvestigatorId = activeInvestigatorId, + isClassTextureEnabled = isClassTextureEnabled, isDrawButtonVisible = isDrawButtonVisible, playerColor = playerColor, slotData = slotData @@ -111,6 +121,7 @@ function onLoad(savedData) local loadedData = JSON.decode(savedData) activeInvestigatorClass = loadedData.activeInvestigatorClass activeInvestigatorId = loadedData.activeInvestigatorId + isClassTextureEnabled = loadedData.isClassTextureEnabled isDrawButtonVisible = loadedData.isDrawButtonVisible playerColor = loadedData.playerColor slotData = loadedData.slotData @@ -169,7 +180,7 @@ function searchArea(origin, size, filter) return searchLib.inArea(origin, self.getRotation(), size, filter) end --- finds all objects on the playmat and associated set aside zone. +-- finds all objects on the playermat and associated set aside zone. function searchAroundSelf(filter) local scale = self.getScale() local bounds = self.getBoundsNormalized() @@ -180,11 +191,11 @@ function searchAroundSelf(filter) bounds.size.z = bounds.size.z + SEARCH_AROUND_SELF_Z_BUFFER -- 'setAsideDirection' accounts for the set aside zone being on the left or right, - -- depending on the table position of the playmat + -- depending on the table position of the playermat local setAsideDirection = bounds.center.z > 0 and 1 or -1 -- Since the cast is centered on the position, shift left or right to keep - -- the non-set aside edge of the cast at the edge of the playmat + -- the non-set aside edge of the cast at the edge of the playermat local localCenter = self.positionToLocal(bounds.center) localCenter.x = localCenter.x + setAsideDirection * SEARCH_AROUND_SELF_X_BUFFER / 2 / scale.x localCenter.z = localCenter.z - SEARCH_AROUND_SELF_Z_BUFFER / 2 / scale.z @@ -391,8 +402,8 @@ function doUpkeep(_, clickedByColor, isRightClick) j = j + 1 Wait.time(function() deckLib.placeOrMergeIntoDeck(cardsToDiscard[i], returnGlobalDiscardPosition(), self.getRotation()) end, j * 0.1) end - - --add some time if there are any cards to discard, if not, draw up to 5 immediately + + -- add some time if there are any cards to discard, if not, draw up to 5 immediately if j > 0 then k = 0.7 + (j * 0.1) else @@ -751,7 +762,7 @@ function changeColor(clickedByColor) end --------------------------------------------------------- --- playmat token spawning +-- playermat token spawning --------------------------------------------------------- -- Finds all customizable cards in this play area and updates their metadata based on the selections @@ -907,10 +918,12 @@ function maybeUpdateActiveInvestigator(card) notes.combatIcons, notes.agilityIcons }) + updateTexture() elseif activeInvestigatorId ~= "00000" then activeInvestigatorClass = "Neutral" activeInvestigatorId = "00000" ownedObjects.InvestigatorSkillTracker.call("updateStats", { 1, 1, 1, 1 }) + updateTexture() else return end @@ -964,7 +977,7 @@ function maybeUpdateActiveInvestigator(card) count[type] = count[type] + 1 if count[type] > 2 then - print("More than two extra tokens of the same type are not supported.") + printToColor("More than two extra tokens of the same type are not supported.", playerColor) else local localSpawnPos = tokenSpawnPos[type][count[type]] local globalSpawnPos = self.positionToWorld(localSpawnPos):add(Vector(0, 0.2, 0)) @@ -978,6 +991,50 @@ function maybeUpdateActiveInvestigator(card) end end +-- updates the texture of the playermat +---@param overrideName? string Force a specific texture +function updateTexture(overrideName) + local name = "Neutral" + + -- use class specific texture if enabled + if isClassTextureEnabled then + name = activeInvestigatorClass + end + + -- get new texture URL + local newUrl = nameToTexture[name] + + -- override name if valid + if nameToTexture[overrideName] then + newUrl = nameToTexture[overrideName] + end + + -- apply texture + local customInfo = self.getCustomObject() + if customInfo.image ~= newUrl then + -- temporarily lock objects so they don't fall through the mat + local objectsToUnlock = {} + for _, obj in ipairs(searchAroundSelf()) do + if not obj.getLock() then + obj.setLock(true) + table.insert(objectsToUnlock, obj) + end + end + + self.script_state = onSave() + customInfo.image = newUrl + self.setCustomObject(customInfo) + local reloadedMat = self.reload() + + -- unlock objects when mat is reloaded + Wait.condition(function() + for _, obj in ipairs(objectsToUnlock) do + obj.setLock(false) + end + end, function() return reloadedMat.loading_custom == false end) + end +end + --------------------------------------------------------- -- manipulation of owned objects --------------------------------------------------------- @@ -1009,7 +1066,7 @@ function resetSkillTracker() if obj ~= nil then obj.call("updateStats", { 1, 1, 1, 1 }) else - printToAll("Skill tracker for " .. matColor .. " playmat could not be found.", "Yellow") + printToAll("Skill tracker for " .. matColor .. " playermat could not be found.", "Yellow") end end @@ -1079,7 +1136,7 @@ function showDrawButton(visible) end end --- shows / hides a clickable clue counter for this playmat and sets the correct amount of clues +-- shows / hides a clickable clue counter for this playermat and sets the correct amount of clues ---@param showCounter boolean Whether the clickable clue counter should be visible function clickableClues(showCounter) local clickerPos = ownedObjects.ClickableClueCounter.getPosition() @@ -1111,6 +1168,14 @@ function clickableClues(showCounter) end end +-- Toggles the use of class textures +---@param state boolean Whether the class texture should be used or not +function useClassTexture(state) + if state == isClassTextureEnabled then return end + isClassTextureEnabled = state + updateTexture() +end + -- removes all clues (moving tokens to the trash and setting counters to 0) function removeClues() ownedObjects.ClueCounter.call("removeAllClues", ownedObjects.Trash) diff --git a/src/playermat/PlaymatApi.ttslua b/src/playermat/PlayermatApi.ttslua similarity index 54% rename from src/playermat/PlaymatApi.ttslua rename to src/playermat/PlayermatApi.ttslua index 58b8461d..aab81bb7 100644 --- a/src/playermat/PlaymatApi.ttslua +++ b/src/playermat/PlayermatApi.ttslua @@ -1,11 +1,11 @@ do - local PlaymatApi = {} + local PlayermatApi = {} local guidReferenceApi = require("core/GUIDReferenceApi") local searchLib = require("util/SearchLib") -- Convenience function to look up a mat's object by color, or get all mats. - ---@param matColor string Color of the playmat - White, Orange, Green, Red or All - ---@return table: Single-element if only single playmat is requested + ---@param matColor string Color of the playermat - White, Orange, Green, Red or All + ---@return table: Single-element if only single playermat is requested local function getMatForColor(matColor) if matColor == "All" then return guidReferenceApi.getObjectsByType("Playermat") @@ -14,9 +14,9 @@ do end end - -- Returns the color of the closest playmat + -- Returns the color of the closest playermat ---@param startPos table Starting position to get the closest mat from - PlaymatApi.getMatColorByPosition = function(startPos) + PlayermatApi.getMatColorByPosition = function(startPos) local result, smallestDistance for matColor, mat in pairs(getMatForColor("All")) do local distance = Vector.between(startPos, mat.getPosition()):magnitude() @@ -28,17 +28,17 @@ do return result end - -- Returns the color of the player's hand that is seated next to the playmat - ---@param matColor string Color of the playmat - White, Orange, Green or Red (does not support "All") - PlaymatApi.getPlayerColor = function(matColor) + -- Returns the color of the player's hand that is seated next to the playermat + ---@param matColor string Color of the playermat - White, Orange, Green or Red (does not support "All") + PlayermatApi.getPlayerColor = function(matColor) for _, mat in pairs(getMatForColor(matColor)) do return mat.getVar("playerColor") end end - -- Returns the color of the playmat that owns the playercolor's hand - ---@param handColor string Color of the playmat - PlaymatApi.getMatColor = function(handColor) + -- Returns the color of the playermat that owns the playercolor's hand + ---@param handColor string Color of the playermat + PlayermatApi.getMatColor = function(handColor) for matColor, mat in pairs(getMatForColor("All")) do local playerColor = mat.getVar("playerColor") if playerColor == handColor then @@ -47,35 +47,35 @@ do end end - -- Instructs a playmat to check for DES - ---@param matColor string Color of the playmat - White, Orange, Green, Red or All - PlaymatApi.checkForDES = function(matColor) + -- Instructs a playermat to check for DES + ---@param matColor string Color of the playermat - White, Orange, Green, Red or All + PlayermatApi.checkForDES = function(matColor) for _, mat in pairs(getMatForColor(matColor)) do mat.call("checkForDES") end end - -- Returns if there is the card "Dream-Enhancing Serum" on the requested playmat - ---@param matColor string Color of the playmat - White, Orange, Green or Red (does not support "All") - ---@return boolean: whether DES is present on the playmat - PlaymatApi.hasDES = function(matColor) + -- Returns if there is the card "Dream-Enhancing Serum" on the requested playermat + ---@param matColor string Color of the playermat - White, Orange, Green or Red (does not support "All") + ---@return boolean: whether DES is present on the playermat + PlayermatApi.hasDES = function(matColor) for _, mat in pairs(getMatForColor(matColor)) do return mat.getVar("hasDES") end end - -- gets the slot data for the playmat - ---@param matColor string Color of the playmat - White, Orange, Green or Red (does not support "All") - PlaymatApi.getSlotData = function(matColor) + -- gets the slot data for the playermat + ---@param matColor string Color of the playermat - White, Orange, Green or Red (does not support "All") + PlayermatApi.getSlotData = function(matColor) for _, mat in pairs(getMatForColor(matColor)) do return mat.getTable("slotData") end end - -- sets the slot data for the playmat - ---@param matColor string Color of the playmat - White, Orange, Green or Red (does not support "All") - ---@param newSlotData table New slot data for the playmat - PlaymatApi.loadSlotData = function(matColor, newSlotData) + -- sets the slot data for the playermat + ---@param matColor string Color of the playermat - White, Orange, Green or Red (does not support "All") + ---@param newSlotData table New slot data for the playermat + PlayermatApi.loadSlotData = function(matColor, newSlotData) for _, mat in pairs(getMatForColor(matColor)) do mat.setTable("slotData", newSlotData) mat.call("redrawSlotSymbols") @@ -83,33 +83,33 @@ do end end - -- Performs a search of the deck area of the requested playmat and returns the result as table - ---@param matColor string Color of the playmat - White, Orange, Green or Red (does not support "All") - PlaymatApi.getDeckAreaObjects = function(matColor) + -- Performs a search of the deck area of the requested playermat and returns the result as table + ---@param matColor string Color of the playermat - White, Orange, Green or Red (does not support "All") + PlayermatApi.getDeckAreaObjects = function(matColor) for _, mat in pairs(getMatForColor(matColor)) do return mat.call("getDeckAreaObjects") end end -- Flips the top card of the deck (useful after deck manipulation for Norman Withers) - ---@param matColor string Color of the playmat - White, Orange, Green or Red (does not support "All") - PlaymatApi.flipTopCardFromDeck = function(matColor) + ---@param matColor string Color of the playermat - White, Orange, Green or Red (does not support "All") + PlayermatApi.flipTopCardFromDeck = function(matColor) for _, mat in pairs(getMatForColor(matColor)) do return mat.call("flipTopCardFromDeck") end end - -- Returns the position of the discard pile of the requested playmat - ---@param matColor string Color of the playmat - White, Orange, Green or Red (does not support "All") - PlaymatApi.getDiscardPosition = function(matColor) + -- Returns the position of the discard pile of the requested playermat + ---@param matColor string Color of the playermat - White, Orange, Green or Red (does not support "All") + PlayermatApi.getDiscardPosition = function(matColor) for _, mat in pairs(getMatForColor(matColor)) do return mat.call("returnGlobalDiscardPosition") end end - -- Returns the position of the draw pile of the requested playmat - ---@param matColor string Color of the playmat - White, Orange, Green or Red (does not support "All") - PlaymatApi.getDrawPosition = function(matColor) + -- Returns the position of the draw pile of the requested playermat + ---@param matColor string Color of the playermat - White, Orange, Green or Red (does not support "All") + PlayermatApi.getDrawPosition = function(matColor) for _, mat in pairs(getMatForColor(matColor)) do return mat.call("returnGlobalDrawPosition") end @@ -117,25 +117,25 @@ do -- Transforms a local position into a global position ---@param localPos table Local position to be transformed - ---@param matColor string Color of the playmat - White, Orange, Green or Red (does not support "All") - PlaymatApi.transformLocalPosition = function(localPos, matColor) + ---@param matColor string Color of the playermat - White, Orange, Green or Red (does not support "All") + PlayermatApi.transformLocalPosition = function(localPos, matColor) for _, mat in pairs(getMatForColor(matColor)) do return mat.positionToWorld(localPos) end end - -- Returns the rotation of the requested playmat - ---@param matColor string Color of the playmat - White, Orange, Green or Red (does not support "All") - PlaymatApi.returnRotation = function(matColor) + -- Returns the rotation of the requested playermat + ---@param matColor string Color of the playermat - White, Orange, Green or Red (does not support "All") + PlayermatApi.returnRotation = function(matColor) for _, mat in pairs(getMatForColor(matColor)) do return mat.getRotation() end end -- Returns a table with spawn data (position and rotation) for a helper object - ---@param matColor string Color of the playmat - White, Orange, Green, Red or All + ---@param matColor string Color of the playermat - White, Orange, Green, Red or All ---@param helperName string Name of the helper object - PlaymatApi.getHelperSpawnData = function(matColor, helperName) + PlayermatApi.getHelperSpawnData = function(matColor, helperName) local resultTable = {} local localPositionTable = { ["Hand Helper"] = {0.05, 0, -1.182}, @@ -152,90 +152,99 @@ do end - -- Triggers the Upkeep for the requested playmat - ---@param matColor string Color of the playmat - White, Orange, Green, Red or All + -- Triggers the Upkeep for the requested playermat + ---@param matColor string Color of the playermat - White, Orange, Green, Red or All ---@param playerColor string Color of the calling player (for messages) - PlaymatApi.doUpkeepFromHotkey = function(matColor, playerColor) + PlayermatApi.doUpkeepFromHotkey = function(matColor, playerColor) for _, mat in pairs(getMatForColor(matColor)) do mat.call("doUpkeepFromHotkey", playerColor) end end - -- Handles discarding for the requested playmat for the provided list of objects - ---@param matColor string Color of the playmat - White, Orange, Green or Red (does not support "All") + -- Handles discarding for the requested playermat for the provided list of objects + ---@param matColor string Color of the playermat - White, Orange, Green or Red (does not support "All") ---@param objList table List of objects to discard - PlaymatApi.discardListOfObjects = function(matColor, objList) + PlayermatApi.discardListOfObjects = function(matColor, objList) for _, mat in pairs(getMatForColor(matColor)) do mat.call("discardListOfObjects", objList) end end -- Returns the active investigator id - ---@param matColor string Color of the playmat - White, Orange, Green or Red (does not support "All") - PlaymatApi.returnInvestigatorId = function(matColor) + ---@param matColor string Color of the playermat - White, Orange, Green or Red (does not support "All") + PlayermatApi.returnInvestigatorId = function(matColor) for _, mat in pairs(getMatForColor(matColor)) do return mat.getVar("activeInvestigatorId") end end -- Returns the class of the active investigator - ---@param matColor string Color of the playmat - White, Orange, Green or Red (does not support "All") - PlaymatApi.returnInvestigatorClass = function(matColor) + ---@param matColor string Color of the playermat - White, Orange, Green or Red (does not support "All") + PlayermatApi.returnInvestigatorClass = function(matColor) for _, mat in pairs(getMatForColor(matColor)) do return mat.getVar("activeInvestigatorClass") end end -- Returns the position for encounter card drawing - ---@param matColor string Color of the playmat - White, Orange, Green or Red (does not support "All") + ---@param matColor string Color of the playermat - White, Orange, Green or Red (does not support "All") ---@param stack boolean If true, returns the leftmost position instead of the first empty from the right - PlaymatApi.getEncounterCardDrawPosition = function(matColor, stack) + PlayermatApi.getEncounterCardDrawPosition = function(matColor, stack) for _, mat in pairs(getMatForColor(matColor)) do return Vector(mat.call("getEncounterCardDrawPosition", stack)) end end - -- Sets the requested playmat's snap points to limit snapping to matching card types or not. If + -- Sets the requested playermat's snap points to limit snapping to matching card types or not. If -- matchTypes is true, the main card slot snap points will only snap assets, while the -- investigator area point will only snap Investigators. If matchTypes is false, snap points will -- be reset to snap all cards. ---@param matchCardTypes boolean Whether snap points should only snap for the matching card types - ---@param matColor string Color of the playmat - White, Orange, Green, Red or All - PlaymatApi.setLimitSnapsByType = function(matchCardTypes, matColor) + ---@param matColor string Color of the playermat - White, Orange, Green, Red or All + PlayermatApi.setLimitSnapsByType = function(matchCardTypes, matColor) for _, mat in pairs(getMatForColor(matColor)) do mat.call("setLimitSnapsByType", matchCardTypes) end end - -- Sets the requested playmat's draw 1 button to visible + -- Sets the requested playermat's draw 1 button to visible ---@param isDrawButtonVisible boolean Whether the draw 1 button should be visible or not - ---@param matColor string Color of the playmat - White, Orange, Green, Red or All - PlaymatApi.showDrawButton = function(isDrawButtonVisible, matColor) + ---@param matColor string Color of the playermat - White, Orange, Green, Red or All + PlayermatApi.showDrawButton = function(isDrawButtonVisible, matColor) for _, mat in pairs(getMatForColor(matColor)) do mat.call("showDrawButton", isDrawButtonVisible) end end - -- Shows or hides the clickable clue counter for the requested playmat + -- Shows or hides the clickable clue counter for the requested playermat ---@param showCounter boolean Whether the clickable counter should be present or not - ---@param matColor string Color of the playmat - White, Orange, Green, Red or All - PlaymatApi.clickableClues = function(showCounter, matColor) + ---@param matColor string Color of the playermat - White, Orange, Green, Red or All + PlayermatApi.clickableClues = function(showCounter, matColor) for _, mat in pairs(getMatForColor(matColor)) do mat.call("clickableClues", showCounter) end end - -- Removes all clues (to the trash for tokens and counters set to 0) for the requested playmat - ---@param matColor string Color of the playmat - White, Orange, Green, Red or All - PlaymatApi.removeClues = function(matColor) + -- Toggles the use of class textures for the requested playermat + ---@param state boolean Whether the class texture should be used or not + ---@param matColor string Color of the playermat - White, Orange, Green, Red or All + PlayermatApi.useClassTexture = function(state, matColor) + for _, mat in pairs(getMatForColor(matColor)) do + mat.call("useClassTexture", state) + end + end + + -- Removes all clues (to the trash for tokens and counters set to 0) for the requested playermat + ---@param matColor string Color of the playermat - White, Orange, Green, Red or All + PlayermatApi.removeClues = function(matColor) for _, mat in pairs(getMatForColor(matColor)) do mat.call("removeClues") end end - -- Reports the clue count for the requested playmat + -- Reports the clue count for the requested playermat ---@param useClickableCounters boolean Controls which type of counter is getting checked - PlaymatApi.getClueCount = function(useClickableCounters, matColor) + PlayermatApi.getClueCount = function(useClickableCounters, matColor) local count = 0 for _, mat in pairs(getMatForColor(matColor)) do count = count + mat.call("getClueCount", useClickableCounters) @@ -244,36 +253,36 @@ do end -- Updates the specified owned counter - ---@param matColor string Color of the playmat - White, Orange, Green, Red or All + ---@param matColor string Color of the playermat - White, Orange, Green, Red or All ---@param type string Counter to target ---@param newValue number Value to set the counter to ---@param modifier number If newValue is not provided, the existing value will be adjusted by this modifier - PlaymatApi.updateCounter = function(matColor, type, newValue, modifier) + PlayermatApi.updateCounter = function(matColor, type, newValue, modifier) for _, mat in pairs(getMatForColor(matColor)) do mat.call("updateCounter", { type = type, newValue = newValue, modifier = modifier }) end end - -- Triggers the draw function for the specified playmat - ---@param matColor string Color of the playmat - White, Orange, Green, Red or All + -- Triggers the draw function for the specified playermat + ---@param matColor string Color of the playermat - White, Orange, Green, Red or All ---@param number number Amount of cards to draw - PlaymatApi.drawCardsWithReshuffle = function(matColor, number) + PlayermatApi.drawCardsWithReshuffle = function(matColor, number) for _, mat in pairs(getMatForColor(matColor)) do mat.call("drawCardsWithReshuffle", number) end end -- Returns the resource counter amount - ---@param matColor string Color of the playmat - White, Orange, Green or Red (does not support "All") + ---@param matColor string Color of the playermat - White, Orange, Green or Red (does not support "All") ---@param type string Counter to target - PlaymatApi.getCounterValue = function(matColor, type) + PlayermatApi.getCounterValue = function(matColor, type) for _, mat in pairs(getMatForColor(matColor)) do return mat.call("getCounterValue", type) end end -- Returns a list of mat colors that have an investigator placed - PlaymatApi.getUsedMatColors = function() + PlayermatApi.getUsedMatColors = function() local localInvestigatorPosition = { x = -1.17, y = 1, z = -0.01 } local usedColors = {} for matColor, mat in pairs(getMatForColor("All")) do @@ -287,25 +296,25 @@ do end -- Resets the specified skill tracker to "1, 1, 1, 1" - ---@param matColor string Color of the playmat - White, Orange, Green, Red or All - PlaymatApi.resetSkillTracker = function(matColor) + ---@param matColor string Color of the playermat - White, Orange, Green, Red or All + PlayermatApi.resetSkillTracker = function(matColor) for _, mat in pairs(getMatForColor(matColor)) do mat.call("resetSkillTracker") end end -- Redraws the XML for the slot symbols based on the slotData table - ---@param matColor string Color of the playmat - White, Orange, Green, Red or All - PlaymatApi.redrawSlotSymbols = function(matColor) + ---@param matColor string Color of the playermat - White, Orange, Green, Red or All + PlayermatApi.redrawSlotSymbols = function(matColor) for _, mat in pairs(getMatForColor(matColor)) do mat.call("redrawSlotSymbols") end end - -- Finds all objects on the playmat and associated set aside zone and returns a table - ---@param matColor string Color of the playmat - White, Orange, Green, Red or All + -- Finds all objects on the playermat and associated set aside zone and returns a table + ---@param matColor string Color of the playermat - White, Orange, Green, Red or All ---@param filter string Name of the filte function (see util/SearchLib) - PlaymatApi.searchAroundPlaymat = function(matColor, filter) + PlayermatApi.searchAroundPlayermat = function(matColor, filter) local objList = {} for _, mat in pairs(getMatForColor(matColor)) do for _, obj in ipairs(mat.call("searchAroundSelf", filter)) do @@ -316,19 +325,19 @@ do end -- Discard a non-hidden card from the corresponding player's hand - ---@param matColor string Color of the playmat - White, Orange, Green, Red or All - PlaymatApi.doDiscardOne = function(matColor) + ---@param matColor string Color of the playermat - White, Orange, Green, Red or All + PlayermatApi.doDiscardOne = function(matColor) for _, mat in pairs(getMatForColor(matColor)) do mat.call("doDiscardOne") end end - -- Triggers the metadata sync for all playmats - PlaymatApi.syncAllCustomizableCards = function() + -- Triggers the metadata sync for all playermats + PlayermatApi.syncAllCustomizableCards = function() for _, mat in pairs(getMatForColor("All")) do mat.call("syncAllCustomizableCards") end end - return PlaymatApi + return PlayermatApi end diff --git a/src/playermat/Zones.ttslua b/src/playermat/Zones.ttslua index 551da198..36f4742b 100644 --- a/src/playermat/Zones.ttslua +++ b/src/playermat/Zones.ttslua @@ -20,7 +20,7 @@ -- SetAside5: Hunch Deck for Joe Diamond -- SetAside6: currently unused do - local playmatApi = require("playermat/PlaymatApi") + local playermatApi = require("playermat/PlayermatApi") local Zones = { } local commonZones = {} @@ -126,7 +126,7 @@ do and playerColor ~= "Green") then return nil end - return playmatApi.transformLocalPosition(zoneData[playerColor][zoneName], playerColor) + return playermatApi.transformLocalPosition(zoneData[playerColor][zoneName], playerColor) end -- Return the global rotation for a card on the given player mat, based on its zone. @@ -136,7 +136,7 @@ do -- Y rotation to orient the card on the given player mat as well as a -- Z rotation to place the card face up or face down. Zones.getDefaultCardRotation = function(playerColor, zoneName) - local cardRotation = playmatApi.returnRotation(playerColor) + local cardRotation = playermatApi.returnRotation(playerColor) if zoneName == "Deck" then cardRotation = cardRotation + Vector(0, 0, 180) end diff --git a/src/util/TokenSpawnTool.ttslua b/src/util/TokenSpawnTool.ttslua index 66f43a75..31d411a6 100644 --- a/src/util/TokenSpawnTool.ttslua +++ b/src/util/TokenSpawnTool.ttslua @@ -1,4 +1,4 @@ -local playmatApi = require("playermat/PlaymatApi") +local playermatApi = require("playermat/PlayermatApi") local searchLib = require("util/SearchLib") local tokenManager = require("core/token/TokenManager") local TOKEN_INDEX = {} @@ -79,8 +79,8 @@ function onScriptingButtonDown(index, playerColor) end -- check for nearest investigator card and change action token state to its class elseif tokenType == "universalActionAbility" then - local matColor = playmatApi.getMatColorByPosition(position) - local class = playmatApi.returnInvestigatorClass(matColor) + local matColor = playermatApi.getMatColorByPosition(position) + local class = playermatApi.returnInvestigatorClass(matColor) callback = function(spawned) spawned.call("updateClassAndSymbol", { class = class, symbol = class }) end end diff --git a/xml/Global/OptionPanel.xml b/xml/Global/OptionPanel.xml index e7d79f3a..f5246678 100644 --- a/xml/Global/OptionPanel.xml +++ b/xml/Global/OptionPanel.xml @@ -288,6 +288,21 @@ + + + + + Use class-specific texture + + + +