Merge pull request #21 from argonui/playermats

updated playermats and added InvestigatorSkillTracker
This commit is contained in:
Chr1Z 2022-11-17 00:22:46 +01:00 committed by GitHub
commit 90ed79ee96
No known key found for this signature in database
GPG Key ID: 4AEE18F83AFDEB23
28 changed files with 620 additions and 1472 deletions

View File

@ -206,27 +206,11 @@
"EdgeoftheEarth.895eaa",
"TheDream-Eaters.a16a1a",
"ReturntoTheCircleUndone.757324",
"Intellect.0016fc",
"Playermat4Red.0840d5",
"Agility.181fa2",
"Combat.19026b",
"Agility.2c3f8d",
"Playermat3Green.383d8b",
"Intellect.4ca990",
"MiscDoominplay.652ff3",
"Willpower.85a8ed",
"Playermat1White.8b081b",
"Willpower.8b6743",
"Combat.9136c6",
"Combat.93a48b",
"Agility.a0b6df",
"Willpower.afc290",
"Intellect.b4ef12",
"Combat.b661a6",
"Playermat2Orange.bd0ff4",
"Intellect.c1fe65",
"Agility.d4df33",
"Willpower.fa6df4",
"CustomDataHelper.2547b3",
"LolaNeutral.637e17",
"LolaNeutral.e003fe",
@ -258,7 +242,11 @@
"PhaseTracker.d0c8fa",
"AllPlayerCards.15bb07",
"Search-A-Card.24051a",
"231Notes-10152022.268764"
"231Notes-10152022.268764",
"InvestigatorSkillTracker.af7ed7",
"InvestigatorSkillTracker.e598c2",
"InvestigatorSkillTracker.b4a5f7",
"InvestigatorSkillTracker.e74881"
],
"PlayArea": 1,
"PlayerCounts": [

View File

@ -1,60 +0,0 @@
{
"AltLookAngle": {
"x": 0,
"y": 0,
"z": 0
},
"Autoraise": true,
"ColorDiffuse": {
"b": 1,
"g": 1,
"r": 1
},
"CustomImage": {
"CustomToken": {
"MergeDistancePixels": 5,
"Stackable": false,
"StandUp": false,
"Thickness": 0.1
},
"ImageScalar": 1,
"ImageSecondaryURL": "",
"ImageURL": "https://i.imgur.com/vXVWwD0.png",
"WidthScale": 0
},
"Description": "Left click - Increase\nRight click - Decrease",
"DragSelectable": true,
"GMNotes": "",
"GUID": "2c3f8d",
"Grid": false,
"GridProjection": false,
"Hands": false,
"HideWhenFaceDown": false,
"IgnoreFoW": false,
"LayoutGroupSortIndex": 0,
"Locked": true,
"LuaScript": "require(\"playermat/SkillToken\")",
"LuaScriptState": "[true,0]",
"MeasureMovement": false,
"Name": "Custom_Token",
"Nickname": "Agility",
"Snap": false,
"Sticky": true,
"Tags": [
"CleanUpHelper_ignore"
],
"Tooltip": false,
"Transform": {
"posX": -15.861,
"posY": 1.548,
"posZ": -19.216,
"rotX": 0,
"rotY": 180,
"rotZ": 0,
"scaleX": 0.429196239,
"scaleY": 1,
"scaleZ": 0.429196239
},
"Value": 0,
"XmlUI": ""
}

View File

@ -1,60 +0,0 @@
{
"AltLookAngle": {
"x": 0,
"y": 0,
"z": 0
},
"Autoraise": true,
"ColorDiffuse": {
"b": 1,
"g": 1,
"r": 1
},
"CustomImage": {
"CustomToken": {
"MergeDistancePixels": 5,
"Stackable": false,
"StandUp": false,
"Thickness": 0.1
},
"ImageScalar": 1,
"ImageSecondaryURL": "",
"ImageURL": "https://i.imgur.com/vXVWwD0.png",
"WidthScale": 0
},
"Description": "Left click - Increase\nRight click - Decrease",
"DragSelectable": true,
"GMNotes": "",
"GUID": "a0b6df",
"Grid": false,
"GridProjection": false,
"Hands": false,
"HideWhenFaceDown": false,
"IgnoreFoW": false,
"LayoutGroupSortIndex": 0,
"Locked": true,
"LuaScript": "require(\"playermat/SkillToken\")",
"LuaScriptState": "[true,0]",
"MeasureMovement": false,
"Name": "Custom_Token",
"Nickname": "Agility",
"Snap": false,
"Sticky": true,
"Tags": [
"CleanUpHelper_ignore"
],
"Tooltip": false,
"Transform": {
"posX": -47.642,
"posY": 1.6,
"posZ": 5.825,
"rotX": 0,
"rotY": 270,
"rotZ": 0,
"scaleX": 0.429196239,
"scaleY": 1,
"scaleZ": 0.429196239
},
"Value": 0,
"XmlUI": ""
}

View File

@ -1,60 +0,0 @@
{
"AltLookAngle": {
"x": 0,
"y": 0,
"z": 0
},
"Autoraise": true,
"ColorDiffuse": {
"b": 1,
"g": 1,
"r": 1
},
"CustomImage": {
"CustomToken": {
"MergeDistancePixels": 5,
"Stackable": false,
"StandUp": false,
"Thickness": 0.1
},
"ImageScalar": 1,
"ImageSecondaryURL": "",
"ImageURL": "https://i.imgur.com/vXVWwD0.png",
"WidthScale": 0
},
"Description": "Left click - Increase\nRight click - Decrease",
"DragSelectable": true,
"GMNotes": "",
"GUID": "d4df33",
"Grid": false,
"GridProjection": false,
"Hands": false,
"HideWhenFaceDown": false,
"IgnoreFoW": false,
"LayoutGroupSortIndex": 0,
"Locked": true,
"LuaScript": "require(\"playermat/SkillToken\")",
"LuaScriptState": "[true,0]",
"MeasureMovement": false,
"Name": "Custom_Token",
"Nickname": "Agility",
"Snap": false,
"Sticky": true,
"Tags": [
"CleanUpHelper_ignore"
],
"Tooltip": false,
"Transform": {
"posX": -47.641,
"posY": 1.59,
"posZ": -25.644,
"rotX": 0,
"rotY": 270,
"rotZ": 0,
"scaleX": 0.429196239,
"scaleY": 1,
"scaleZ": 0.429196239
},
"Value": 0,
"XmlUI": ""
}

View File

@ -1,60 +0,0 @@
{
"AltLookAngle": {
"x": 0,
"y": 0,
"z": 0
},
"Autoraise": true,
"ColorDiffuse": {
"b": 1,
"g": 1,
"r": 1
},
"CustomImage": {
"CustomToken": {
"MergeDistancePixels": 5,
"Stackable": false,
"StandUp": false,
"Thickness": 0.1
},
"ImageScalar": 1,
"ImageSecondaryURL": "",
"ImageURL": "https://i.imgur.com/YBjxze6.png",
"WidthScale": 0
},
"Description": "Left click - Increase\nRight click - Decrease",
"DragSelectable": true,
"GMNotes": "",
"GUID": "19026b",
"Grid": false,
"GridProjection": false,
"Hands": false,
"HideWhenFaceDown": false,
"IgnoreFoW": false,
"LayoutGroupSortIndex": 0,
"Locked": true,
"LuaScript": "require(\"playermat/SkillToken\")",
"LuaScriptState": "[true,0]",
"MeasureMovement": false,
"Name": "Custom_Token",
"Nickname": "Combat",
"Snap": false,
"Sticky": true,
"Tags": [
"CleanUpHelper_ignore"
],
"Tooltip": false,
"Transform": {
"posX": -34.137,
"posY": 1.585,
"posZ": 19.236,
"rotX": 0,
"rotY": 0,
"rotZ": 0,
"scaleX": 0.429196239,
"scaleY": 1,
"scaleZ": 0.429196239
},
"Value": 0,
"XmlUI": ""
}

View File

@ -1,60 +0,0 @@
{
"AltLookAngle": {
"x": 0,
"y": 0,
"z": 0
},
"Autoraise": true,
"ColorDiffuse": {
"b": 1,
"g": 1,
"r": 1
},
"CustomImage": {
"CustomToken": {
"MergeDistancePixels": 5,
"Stackable": false,
"StandUp": false,
"Thickness": 0.1
},
"ImageScalar": 1,
"ImageSecondaryURL": "",
"ImageURL": "https://i.imgur.com/sj8GatY.png",
"WidthScale": 0
},
"Description": "Left click - Increase\nRight click - Decrease",
"DragSelectable": true,
"GMNotes": "",
"GUID": "0016fc",
"Grid": false,
"GridProjection": false,
"Hands": false,
"HideWhenFaceDown": false,
"IgnoreFoW": false,
"LayoutGroupSortIndex": 0,
"Locked": true,
"LuaScript": "require(\"playermat/SkillToken\")",
"LuaScriptState": "[true,0]",
"MeasureMovement": false,
"Name": "Custom_Token",
"Nickname": "Intellect",
"Snap": false,
"Sticky": true,
"Tags": [
"CleanUpHelper_ignore"
],
"Tooltip": false,
"Transform": {
"posX": -32.672,
"posY": 1.583,
"posZ": 19.236,
"rotX": 0,
"rotY": 0,
"rotZ": 0,
"scaleX": 0.429196239,
"scaleY": 1,
"scaleZ": 0.429196239
},
"Value": 0,
"XmlUI": ""
}

View File

@ -1,60 +0,0 @@
{
"AltLookAngle": {
"x": 0,
"y": 0,
"z": 0
},
"Autoraise": true,
"ColorDiffuse": {
"b": 1,
"g": 1,
"r": 1
},
"CustomImage": {
"CustomToken": {
"MergeDistancePixels": 5,
"Stackable": false,
"StandUp": false,
"Thickness": 0.1
},
"ImageScalar": 1,
"ImageSecondaryURL": "",
"ImageURL": "https://i.imgur.com/sj8GatY.png",
"WidthScale": 0
},
"Description": "Left click - Increase\nRight click - Decrease",
"DragSelectable": true,
"GMNotes": "",
"GUID": "4ca990",
"Grid": false,
"GridProjection": false,
"Hands": false,
"HideWhenFaceDown": false,
"IgnoreFoW": false,
"LayoutGroupSortIndex": 0,
"Locked": true,
"LuaScript": "require(\"playermat/SkillToken\")",
"LuaScriptState": "[true,0]",
"MeasureMovement": false,
"Name": "Custom_Token",
"Nickname": "Intellect",
"Snap": false,
"Sticky": true,
"Tags": [
"CleanUpHelper_ignore"
],
"Tooltip": false,
"Transform": {
"posX": -47.638,
"posY": 1.591,
"posZ": -22.713,
"rotX": 0,
"rotY": 270,
"rotZ": 0,
"scaleX": 0.429196239,
"scaleY": 1,
"scaleZ": 0.429196239
},
"Value": 0,
"XmlUI": ""
}

View File

@ -1,60 +0,0 @@
{
"AltLookAngle": {
"x": 0,
"y": 0,
"z": 0
},
"Autoraise": true,
"ColorDiffuse": {
"b": 1,
"g": 1,
"r": 1
},
"CustomImage": {
"CustomToken": {
"MergeDistancePixels": 5,
"Stackable": false,
"StandUp": false,
"Thickness": 0.1
},
"ImageScalar": 1,
"ImageSecondaryURL": "",
"ImageURL": "https://i.imgur.com/sj8GatY.png",
"WidthScale": 0
},
"Description": "Left click - Increase\nRight click - Decrease",
"DragSelectable": true,
"GMNotes": "",
"GUID": "b4ef12",
"Grid": false,
"GridProjection": false,
"Hands": false,
"HideWhenFaceDown": false,
"IgnoreFoW": false,
"LayoutGroupSortIndex": 0,
"Locked": true,
"LuaScript": "require(\"playermat/SkillToken\")",
"LuaScriptState": "[true,0]",
"MeasureMovement": false,
"Name": "Custom_Token",
"Nickname": "Intellect",
"Snap": false,
"Sticky": true,
"Tags": [
"CleanUpHelper_ignore"
],
"Tooltip": false,
"Transform": {
"posX": -18.79,
"posY": 1.552,
"posZ": -19.216,
"rotX": 0,
"rotY": 180,
"rotZ": 0,
"scaleX": 0.429196239,
"scaleY": 1,
"scaleZ": 0.429196239
},
"Value": 0,
"XmlUI": ""
}

View File

@ -1,60 +0,0 @@
{
"AltLookAngle": {
"x": 0,
"y": 0,
"z": 0
},
"Autoraise": true,
"ColorDiffuse": {
"b": 1,
"g": 1,
"r": 1
},
"CustomImage": {
"CustomToken": {
"MergeDistancePixels": 5,
"Stackable": false,
"StandUp": false,
"Thickness": 0.1
},
"ImageScalar": 1,
"ImageSecondaryURL": "",
"ImageURL": "https://i.imgur.com/sj8GatY.png",
"WidthScale": 0
},
"Description": "Left click - Increase\nRight click - Decrease",
"DragSelectable": true,
"GMNotes": "",
"GUID": "c1fe65",
"Grid": false,
"GridProjection": false,
"Hands": false,
"HideWhenFaceDown": false,
"IgnoreFoW": false,
"LayoutGroupSortIndex": 0,
"Locked": true,
"LuaScript": "require(\"playermat/SkillToken\")",
"LuaScriptState": "[true,0]",
"MeasureMovement": false,
"Name": "Custom_Token",
"Nickname": "Intellect",
"Snap": false,
"Sticky": true,
"Tags": [
"CleanUpHelper_ignore"
],
"Tooltip": false,
"Transform": {
"posX": -47.642,
"posY": 1.601,
"posZ": 8.755,
"rotX": 0,
"rotY": 270,
"rotZ": 0,
"scaleX": 0.429196239,
"scaleY": 1,
"scaleZ": 0.429196239
},
"Value": 0,
"XmlUI": ""
}

View File

@ -19,41 +19,42 @@
},
"ImageScalar": 1,
"ImageSecondaryURL": "",
"ImageURL": "https://i.imgur.com/vXVWwD0.png",
"ImageURL": "http://cloud-3.steamusercontent.com/ugc/1910115722579978285/38E3156A777396FF8C96D2191720790162749C40/",
"WidthScale": 0
},
"Description": "Left click - Increase\nRight click - Decrease",
"Description": "Displays the stats of your investigator and can be clicked to increase / decrease the stats.\n\nSee context menu for additional information.",
"DragSelectable": true,
"GMNotes": "",
"GUID": "181fa2",
"Grid": false,
"GUID": "af7ed7",
"Grid": true,
"GridProjection": false,
"Hands": false,
"HideWhenFaceDown": false,
"IgnoreFoW": false,
"LayoutGroupSortIndex": 0,
"Locked": true,
"LuaScript": "require(\"playermat/SkillToken\")",
"LuaScriptState": "[true,0]",
"LuaScript": "require(\"playermat/InvestigatorSkillTracker\")",
"LuaScriptState": "[1,1,1,1]",
"MeasureMovement": false,
"Name": "Custom_Token",
"Nickname": "Agility",
"Snap": false,
"Nickname": "Investigator Skill Tracker",
"Snap": true,
"Sticky": true,
"Tags": [
"CleanUpHelper_ignore"
"CleanUpHelper_ignore",
"displacement_excluded"
],
"Tooltip": false,
"Tooltip": true,
"Transform": {
"posX": -35.602,
"posY": 1.587,
"posZ": 19.236,
"posX": -32,
"posY": 1.531,
"posZ": 19.3,
"rotX": 0,
"rotY": 0,
"rotZ": 0,
"scaleX": 0.429196239,
"scaleX": 0.95,
"scaleY": 1,
"scaleZ": 0.429196239
"scaleZ": 0.95
},
"Value": 0,
"XmlUI": ""

View File

@ -19,41 +19,42 @@
},
"ImageScalar": 1,
"ImageSecondaryURL": "",
"ImageURL": "https://i.imgur.com/YBjxze6.png",
"ImageURL": "http://cloud-3.steamusercontent.com/ugc/1910115722579978285/38E3156A777396FF8C96D2191720790162749C40/",
"WidthScale": 0
},
"Description": "Left click - Increase\nRight click - Decrease",
"Description": "Displays the stats of your investigator and can be clicked to increase / decrease the stats.\n\nSee context menu for additional information.",
"DragSelectable": true,
"GMNotes": "",
"GUID": "b661a6",
"Grid": false,
"GUID": "b4a5f7",
"Grid": true,
"GridProjection": false,
"Hands": false,
"HideWhenFaceDown": false,
"IgnoreFoW": false,
"LayoutGroupSortIndex": 0,
"Locked": true,
"LuaScript": "require(\"playermat/SkillToken\")",
"LuaScriptState": "[true,0]",
"LuaScript": "require(\"playermat/InvestigatorSkillTracker\")",
"LuaScriptState": "[1,1,1,1]",
"MeasureMovement": false,
"Name": "Custom_Token",
"Nickname": "Combat",
"Snap": false,
"Nickname": "Investigator Skill Tracker",
"Snap": true,
"Sticky": true,
"Tags": [
"CleanUpHelper_ignore"
"CleanUpHelper_ignore",
"displacement_excluded"
],
"Tooltip": false,
"Tooltip": true,
"Transform": {
"posX": -47.641,
"posY": 1.591,
"posZ": -24.179,
"posX": -47.75,
"posY": 1.531,
"posZ": -22,
"rotX": 0,
"rotY": 270,
"rotZ": 0,
"scaleX": 0.429196239,
"scaleX": 0.95,
"scaleY": 1,
"scaleZ": 0.429196239
"scaleZ": 0.95
},
"Value": 0,
"XmlUI": ""

View File

@ -19,41 +19,42 @@
},
"ImageScalar": 1,
"ImageSecondaryURL": "",
"ImageURL": "https://i.imgur.com/YBjxze6.png",
"ImageURL": "http://cloud-3.steamusercontent.com/ugc/1910115722579978285/38E3156A777396FF8C96D2191720790162749C40/",
"WidthScale": 0
},
"Description": "Left click - Increase\nRight click - Decrease",
"Description": "Displays the stats of your investigator and can be clicked to increase / decrease the stats.\n\nSee context menu for additional information.",
"DragSelectable": true,
"GMNotes": "",
"GUID": "9136c6",
"Grid": false,
"GUID": "e598c2",
"Grid": true,
"GridProjection": false,
"Hands": false,
"HideWhenFaceDown": false,
"IgnoreFoW": false,
"LayoutGroupSortIndex": 0,
"Locked": true,
"LuaScript": "require(\"playermat/SkillToken\")",
"LuaScriptState": "[true,0]",
"LuaScript": "require(\"playermat/InvestigatorSkillTracker\")",
"LuaScriptState": "[1,1,1,1]",
"MeasureMovement": false,
"Name": "Custom_Token",
"Nickname": "Combat",
"Snap": false,
"Nickname": "Investigator Skill Tracker",
"Snap": true,
"Sticky": true,
"Tags": [
"CleanUpHelper_ignore"
"CleanUpHelper_ignore",
"displacement_excluded"
],
"Tooltip": false,
"Tooltip": true,
"Transform": {
"posX": -47.642,
"posY": 1.6,
"posZ": 7.29,
"posX": -47.75,
"posY": 1.531,
"posZ": 9,
"rotX": 0,
"rotY": 270,
"rotZ": 0,
"scaleX": 0.429196239,
"scaleX": 0.95,
"scaleY": 1,
"scaleZ": 0.429196239
"scaleZ": 0.95
},
"Value": 0,
"XmlUI": ""

View File

@ -19,41 +19,42 @@
},
"ImageScalar": 1,
"ImageSecondaryURL": "",
"ImageURL": "https://i.imgur.com/YBjxze6.png",
"ImageURL": "http://cloud-3.steamusercontent.com/ugc/1910115722579978285/38E3156A777396FF8C96D2191720790162749C40/",
"WidthScale": 0
},
"Description": "Left click - Increase\nRight click - Decrease",
"Description": "Displays the stats of your investigator and can be clicked to increase / decrease the stats.\n\nSee context menu for additional information.",
"DragSelectable": true,
"GMNotes": "",
"GUID": "93a48b",
"Grid": false,
"GUID": "e74881",
"Grid": true,
"GridProjection": false,
"Hands": false,
"HideWhenFaceDown": false,
"IgnoreFoW": false,
"LayoutGroupSortIndex": 0,
"Locked": true,
"LuaScript": "require(\"playermat/SkillToken\")",
"LuaScriptState": "[true,0]",
"LuaScript": "require(\"playermat/InvestigatorSkillTracker\")",
"LuaScriptState": "[1,1,1,1]",
"MeasureMovement": false,
"Name": "Custom_Token",
"Nickname": "Combat",
"Snap": false,
"Nickname": "Investigator Skill Tracker",
"Snap": true,
"Sticky": true,
"Tags": [
"CleanUpHelper_ignore"
"CleanUpHelper_ignore",
"displacement_excluded"
],
"Tooltip": false,
"Tooltip": true,
"Transform": {
"posX": -17.326,
"posY": 1.55,
"posZ": -19.216,
"posX": -19,
"posY": 1.531,
"posZ": -19.35,
"rotX": 0,
"rotY": 180,
"rotZ": 0,
"scaleX": 0.429196239,
"scaleX": 0.95,
"scaleY": 1,
"scaleZ": 0.429196239
"scaleZ": 0.95
},
"Value": 0,
"XmlUI": ""

View File

@ -228,7 +228,7 @@
"IgnoreFoW": false,
"LayoutGroupSortIndex": 0,
"Locked": true,
"LuaScriptState": "{\"playerColor\":\"White\",\"zoneID\":\"7af2cf\"}",
"LuaScriptState": "{\"activeInvestigatorId\":\"00000\",\"playerColor\":\"White\",\"zoneID\":\"7af2cf\"}",
"LuaScript_path": "Playermat1White.8b081b.ttslua",
"MeasureMovement": false,
"Name": "Custom_Tile",

View File

@ -1,41 +1,15 @@
-- set true to enable debug logging
DEBUG = false
-- we use this to turn off collision handling (for clue spawning)
-- until after load is complete (probably a better way to do this)
COLLISION_ENABLED = false
-- position offsets, adjust these to reposition things relative to mat [x,y,z]
DRAWN_ENCOUNTER_CARD_OFFSET = {1.365, 0.5, -0.635}
DRAWN_CHAOS_TOKEN_OFFSET = {-1.55, 0.5, -0.58}
DISCARD_BUTTON_OFFSETS = {
{-1.365, 0.2, -0.945},
{-0.91, 0.2, -0.945},
{-0.455, 0.2, -0.945},
{0, 0.2, -0.945},
{0.455, 0.2, -0.945},
{0.91, 0.2, -0.945},
}
-- draw deck and discard zone
DECK_POSITION = { x=-1.4, y=0, z=0.3 }
DECK_ZONE_SCALE = { x=3, y=5, z=8 }
DRAW_DECK_POSITION = { x=-54.8, y=2.5, z=4.3 }
---------------------------------------------------------
-- specific setup (different for each playmat)
---------------------------------------------------------
-- play zone
PLAYER_COLOR = "White"
PLAY_ZONE_POSITION = { x=-54.42, y=4.10, z=20.96}
PLAY_ZONE_ROTATION = { x=0, y=270, z=0 }
PLAY_ZONE_SCALE = { x=36.63, y=5.10, z=14.59}
PLAY_ZONE_POSITION = { x = -54.5, y = 4, z = 21 }
PLAY_ZONE_SCALE = { x = 36, y = 5.1, z = 14.5 }
DRAW_DECK_POSITION = { x = -54.8, y = 2.5, z = 4.29 }
DISCARD_PILE_POSITION = { x = -58.9, y = 4, z = 4.29 }
TRASHCAN_GUID = "147e80"
STAT_TRACKER_GUID = "e598c2"
RESOURCE_COUNTER_GUID = "4406f0"
-- the position of the global discard pile
-- TODO: delegate to global for any auto discard actions
DISCARD_POSITION = {-3.85, 3, 10.38}
-- DISCARD PILE POSITION
DISCARD_PILE_POSITION = {-59.13, 4, 4.40 }
local willpowerTokenGuid = "85a8ed"
local intellectTokenGuid = "c1fe65"
local combatTokenGuid = "9136c6"
local agilityTokenGuid = "a0b6df"
require("playermat/Playmat")

View File

@ -228,7 +228,7 @@
"IgnoreFoW": false,
"LayoutGroupSortIndex": 0,
"Locked": true,
"LuaScriptState": "{\"playerColor\":\"Orange\",\"zoneID\":\"b047f8\"}",
"LuaScriptState": "{\"activeInvestigatorId\":\"00000\",\"playerColor\":\"Orange\",\"zoneID\":\"b047f8\"}",
"LuaScript_path": "Playermat2Orange.bd0ff4.ttslua",
"MeasureMovement": false,
"Name": "Custom_Tile",

View File

@ -1,41 +1,15 @@
-- set true to enable debug logging
DEBUG = false
-- we use this to turn off collision handling (for clue spawning)
-- until after load is complete (probably a better way to do this)
COLLISION_ENABLED = false
-- position offsets, adjust these to reposition things relative to mat [x,y,z]
DRAWN_ENCOUNTER_CARD_OFFSET = {1.365, 0.5, -0.635}
DRAWN_CHAOS_TOKEN_OFFSET = {-1.55, 0.5, -0.58}
DISCARD_BUTTON_OFFSETS = {
{-1.365, 0.2, -0.945},
{-0.91, 0.2, -0.945},
{-0.455, 0.2, -0.945},
{0, 0.2, -0.945},
{0.455, 0.2, -0.945},
{0.91, 0.2, -0.945},
}
-- draw deck and discard zone
DECK_POSITION = { x=-1.4, y=0, z=0.3 }
DECK_ZONE_SCALE = { x=3, y=5, z=8 }
DRAW_DECK_POSITION = { x=-55, y=2.5, z=-27.8 }
---------------------------------------------------------
-- specific setup (different for each playmat)
---------------------------------------------------------
-- play zone
PLAYER_COLOR = "Orange"
PLAY_ZONE_POSITION = { x=-54.53, y=4.10, z=-20.94}
PLAY_ZONE_ROTATION = { x=0, y=270, z=0 }
PLAY_ZONE_SCALE = { x=36.96, y=5.10, z=14.70}
PLAY_ZONE_POSITION = { x = -54.5, y = 4, z = -21 }
PLAY_ZONE_SCALE = { x = 36, y = 5.1, z = 14.5 }
DRAW_DECK_POSITION = { x = -54.86, y = 2.5, z = -27.82 }
DISCARD_PILE_POSITION = { x = -58.96, y = 4, z = -27.82 }
TRASHCAN_GUID = "f7b6c8"
STAT_TRACKER_GUID = "b4a5f7"
RESOURCE_COUNTER_GUID = "816d84"
-- the position of the global discard pile
-- TODO: delegate to global for any auto discard actions
DISCARD_POSITION = {-3.85, 3, 10.38}
-- DISCARD PILE POSITION
DISCARD_PILE_POSITION = { -59.19, 4, -22.78 }
local willpowerTokenGuid = "afc290"
local intellectTokenGuid = "4ca990"
local combatTokenGuid = "b661a6"
local agilityTokenGuid = "d4df33"
require("playermat/Playmat")

View File

@ -228,7 +228,7 @@
"IgnoreFoW": false,
"LayoutGroupSortIndex": 0,
"Locked": true,
"LuaScriptState": "{\"playerColor\":\"Green\",\"zoneID\":\"fb28e1\"}",
"LuaScriptState": "{\"activeInvestigatorId\":\"00000\",\"playerColor\":\"Green\",\"zoneID\":\"fb28e1\"}",
"LuaScript_path": "Playermat3Green.383d8b.ttslua",
"MeasureMovement": false,
"Name": "Custom_Tile",

View File

@ -1,41 +1,15 @@
-- set true to enable debug logging
DEBUG = false
-- we use this to turn off collision handling (for clue spawning)
-- until after load is complete (probably a better way to do this)
COLLISION_ENABLED = false
-- position offsets, adjust these to reposition things relative to mat [x,y,z]
DRAWN_ENCOUNTER_CARD_OFFSET = {1.365, 0.5, -0.635}
DRAWN_CHAOS_TOKEN_OFFSET = {-1.55, 0.5, -0.58}
DISCARD_BUTTON_OFFSETS = {
{-1.365, 0.2, -0.945},
{-0.91, 0.2, -0.945},
{-0.455, 0.2, -0.945},
{0, 0.2, -0.945},
{0.455, 0.2, -0.945},
{0.91, 0.2, -0.945},
}
-- draw deck and discard zone
DECK_POSITION = { x=-1.4, y=0, z=0.3 }
DECK_ZONE_SCALE = { x=3, y=5, z=8 }
DRAW_DECK_POSITION = { x=-37.2, y=2.5, z=26.3 }
---------------------------------------------------------
-- specific setup (different for each playmat)
---------------------------------------------------------
-- play zone
PLAYER_COLOR = "Green"
PLAY_ZONE_POSITION = { x = -25, y = 4, z = 27 }
PLAY_ZONE_ROTATION = { x=0, y=0, z=0 }
PLAY_ZONE_SCALE = { x=30, y=5, z=15 }
PLAY_ZONE_SCALE = { x = 30, y = 5, z = 14.5 }
DRAW_DECK_POSITION = { x = -37.26, y = 2.5, z = 26.4 }
DISCARD_PILE_POSITION = { x = -37.26, y = 4, z = 30.50 }
TRASHCAN_GUID = "5f896a"
STAT_TRACKER_GUID = "af7ed7"
RESOURCE_COUNTER_GUID = "cd15ac"
-- the position of the global discard pile
-- TODO: delegate to global for any auto discard actions
DISCARD_POSITION = {-3.85, 3, 10.38}
-- DISCARD PILE POSITION
DISCARD_PILE_POSITION = { -37.11, 4, 30.76 }
local willpowerTokenGuid = "fa6df4"
local intellectTokenGuid = "0016fc"
local combatTokenGuid = "19026b"
local agilityTokenGuid = "181fa2"
require("playermat/Playmat")

View File

@ -228,7 +228,7 @@
"IgnoreFoW": false,
"LayoutGroupSortIndex": 0,
"Locked": true,
"LuaScriptState": "{\"playerColor\":\"Red\",\"zoneID\":\"18538f\"}",
"LuaScriptState": "{\"activeInvestigatorId\":\"00000\",\"playerColor\":\"Red\",\"zoneID\":\"18538f\"}",
"LuaScript_path": "Playermat4Red.0840d5.ttslua",
"MeasureMovement": false,
"Name": "Custom_Tile",

View File

@ -1,41 +1,15 @@
-- set true to enable debug logging
DEBUG = false
-- we use this to turn off collision handling (for clue spawning)
-- until after load is complete (probably a better way to do this)
COLLISION_ENABLED = false
-- position offsets, adjust these to reposition things relative to mat [x,y,z]
DRAWN_ENCOUNTER_CARD_OFFSET = {1.365, 0.5, -0.635}
DRAWN_CHAOS_TOKEN_OFFSET = {-1.55, 0.5, -0.58}
DISCARD_BUTTON_OFFSETS = {
{-1.365, 0.2, -0.945},
{-0.91, 0.2, -0.945},
{-0.455, 0.2, -0.945},
{0, 0.2, -0.945},
{0.455, 0.2, -0.945},
{0.91, 0.2, -0.945},
}
-- draw deck and discard zone
DECK_POSITION = { x=-1.4, y=0, z=0.3 }
DECK_ZONE_SCALE = { x=3, y=5, z=8 }
DRAW_DECK_POSITION = { x=-13.7, y=2.5, z=-26.4 }
---------------------------------------------------------
-- specific setup (different for each playmat)
---------------------------------------------------------
-- play zone
PLAYER_COLOR = "Red"
PLAY_ZONE_POSITION = { x = -25, y = 4, z = -27 }
PLAY_ZONE_ROTATION = { x=0, y=180, z=0 }
PLAY_ZONE_SCALE = { x=30, y=5, z=15 }
PLAY_ZONE_SCALE = { x = 30, y = 5, z = 14.5 }
DRAW_DECK_POSITION = { x = -13.78, y = 2.5, z = -26.37 }
DISCARD_PILE_POSITION = { x = -13.78, y = 4, z = -30.48 }
TRASHCAN_GUID = "4b8594"
STAT_TRACKER_GUID = "e74881"
RESOURCE_COUNTER_GUID = "a4b60d"
-- the position of the global discard pile
-- TODO: delegate to global for any auto discard actions
DISCARD_POSITION = {-3.85, 3, 10.38}
-- DISCARD PILE POSITION
DISCARD_PILE_POSITION = { -18.79, 4, -30.84 }
local willpowerTokenGuid = "8b6743"
local intellectTokenGuid = "b4ef12"
local combatTokenGuid = "93a48b"
local agilityTokenGuid = "2c3f8d"
require("playermat/Playmat")

View File

@ -1,60 +0,0 @@
{
"AltLookAngle": {
"x": 0,
"y": 0,
"z": 0
},
"Autoraise": true,
"ColorDiffuse": {
"b": 1,
"g": 1,
"r": 1
},
"CustomImage": {
"CustomToken": {
"MergeDistancePixels": 5,
"Stackable": false,
"StandUp": false,
"Thickness": 0.1
},
"ImageScalar": 1,
"ImageSecondaryURL": "",
"ImageURL": "https://i.imgur.com/i2IDOcO.png",
"WidthScale": 0
},
"Description": "Left click - Increase\nRight click - Decrease",
"DragSelectable": true,
"GMNotes": "",
"GUID": "85a8ed",
"Grid": false,
"GridProjection": false,
"Hands": false,
"HideWhenFaceDown": false,
"IgnoreFoW": false,
"LayoutGroupSortIndex": 0,
"Locked": true,
"LuaScript": "require(\"playermat/SkillToken\")",
"LuaScriptState": "[true,0]",
"MeasureMovement": false,
"Name": "Custom_Token",
"Nickname": "Willpower",
"Snap": false,
"Sticky": true,
"Tags": [
"CleanUpHelper_ignore"
],
"Tooltip": false,
"Transform": {
"posX": -47.642,
"posY": 1.601,
"posZ": 10.22,
"rotX": 0,
"rotY": 270,
"rotZ": 0,
"scaleX": 0.429196239,
"scaleY": 1,
"scaleZ": 0.429196239
},
"Value": 0,
"XmlUI": ""
}

View File

@ -1,60 +0,0 @@
{
"AltLookAngle": {
"x": 0,
"y": 0,
"z": 0
},
"Autoraise": true,
"ColorDiffuse": {
"b": 1,
"g": 1,
"r": 1
},
"CustomImage": {
"CustomToken": {
"MergeDistancePixels": 5,
"Stackable": false,
"StandUp": false,
"Thickness": 0.1
},
"ImageScalar": 1,
"ImageSecondaryURL": "",
"ImageURL": "https://i.imgur.com/i2IDOcO.png",
"WidthScale": 0
},
"Description": "Left click - Increase\nRight click - Decrease",
"DragSelectable": true,
"GMNotes": "",
"GUID": "8b6743",
"Grid": false,
"GridProjection": false,
"Hands": false,
"HideWhenFaceDown": false,
"IgnoreFoW": false,
"LayoutGroupSortIndex": 0,
"Locked": true,
"LuaScript": "require(\"playermat/SkillToken\")",
"LuaScriptState": "[true,0]",
"MeasureMovement": false,
"Name": "Custom_Token",
"Nickname": "Willpower",
"Snap": false,
"Sticky": true,
"Tags": [
"CleanUpHelper_ignore"
],
"Tooltip": false,
"Transform": {
"posX": -20.253,
"posY": 1.554,
"posZ": -19.216,
"rotX": 0,
"rotY": 180,
"rotZ": 0,
"scaleX": 0.429196239,
"scaleY": 1,
"scaleZ": 0.429196239
},
"Value": 0,
"XmlUI": ""
}

View File

@ -1,60 +0,0 @@
{
"AltLookAngle": {
"x": 0,
"y": 0,
"z": 0
},
"Autoraise": true,
"ColorDiffuse": {
"b": 1,
"g": 1,
"r": 1
},
"CustomImage": {
"CustomToken": {
"MergeDistancePixels": 5,
"Stackable": false,
"StandUp": false,
"Thickness": 0.1
},
"ImageScalar": 1,
"ImageSecondaryURL": "",
"ImageURL": "https://i.imgur.com/i2IDOcO.png",
"WidthScale": 0
},
"Description": "Left click - Increase\nRight click - Decrease",
"DragSelectable": true,
"GMNotes": "",
"GUID": "afc290",
"Grid": false,
"GridProjection": false,
"Hands": false,
"HideWhenFaceDown": false,
"IgnoreFoW": false,
"LayoutGroupSortIndex": 0,
"Locked": true,
"LuaScript": "require(\"playermat/SkillToken\")",
"LuaScriptState": "[true,0]",
"MeasureMovement": false,
"Name": "Custom_Token",
"Nickname": "Willpower",
"Snap": false,
"Sticky": true,
"Tags": [
"CleanUpHelper_ignore"
],
"Tooltip": false,
"Transform": {
"posX": -47.638,
"posY": 1.592,
"posZ": -21.248,
"rotX": 0,
"rotY": 270,
"rotZ": 0,
"scaleX": 0.429196239,
"scaleY": 1,
"scaleZ": 0.429196239
},
"Value": 0,
"XmlUI": ""
}

View File

@ -1,60 +0,0 @@
{
"AltLookAngle": {
"x": 0,
"y": 0,
"z": 0
},
"Autoraise": true,
"ColorDiffuse": {
"b": 1,
"g": 1,
"r": 1
},
"CustomImage": {
"CustomToken": {
"MergeDistancePixels": 5,
"Stackable": false,
"StandUp": false,
"Thickness": 0.1
},
"ImageScalar": 1,
"ImageSecondaryURL": "",
"ImageURL": "https://i.imgur.com/i2IDOcO.png",
"WidthScale": 0
},
"Description": "Left click - Increase\nRight click - Decrease",
"DragSelectable": true,
"GMNotes": "",
"GUID": "fa6df4",
"Grid": false,
"GridProjection": false,
"Hands": false,
"HideWhenFaceDown": false,
"IgnoreFoW": false,
"LayoutGroupSortIndex": 0,
"Locked": true,
"LuaScript": "require(\"playermat/SkillToken\")",
"LuaScriptState": "[true,0]",
"MeasureMovement": false,
"Name": "Custom_Token",
"Nickname": "Willpower",
"Snap": false,
"Sticky": true,
"Tags": [
"CleanUpHelper_ignore"
],
"Tooltip": false,
"Transform": {
"posX": -31.208,
"posY": 1.581,
"posZ": 19.236,
"rotX": 0,
"rotY": 0,
"rotZ": 0,
"scaleX": 0.429196239,
"scaleY": 1,
"scaleZ": 0.429196239
},
"Value": 0,
"XmlUI": ""
}

View File

@ -0,0 +1,66 @@
-- Stat Tracker
-- made by: Chr1Z
-- description: helps tracking the stats of your investigator
local BUTTON_PARAMETERS = {}
BUTTON_PARAMETERS.function_owner = self
BUTTON_PARAMETERS.height = 650
BUTTON_PARAMETERS.width = 700
BUTTON_PARAMETERS.position = { x = -4.775, y = 0.1, z = -0.03 }
BUTTON_PARAMETERS.color = { 0, 0, 0, 0 }
BUTTON_PARAMETERS.font_color = { 0, 0, 0, 100 }
BUTTON_PARAMETERS.font_size = 450
function onSave() return JSON.encode(stats) end
-- load stats and make buttons (left to right)
function onLoad(saved_data)
stats = JSON.decode(saved_data) or { 1, 1, 1, 1 }
for i = 1, 4 do
BUTTON_PARAMETERS.label = stats[i] .. " "
BUTTON_PARAMETERS.position.x = BUTTON_PARAMETERS.position.x + 1.91
BUTTON_PARAMETERS.click_function = attachIndex("button_click", i)
self.createButton(BUTTON_PARAMETERS)
end
self.addContextMenuItem("Reset to 1s", function() updateStats({ 1, 1, 1, 1 }) end)
end
-- helper function to carry index
function attachIndex(click_function, index)
local fn_name = click_function .. index
_G[fn_name] = function(obj, player_color, isRightClick)
_G[click_function](obj, player_color, isRightClick, index)
end
return fn_name
end
function button_click(_, _, isRightClick, index)
stats[index] = math.min(math.max(stats[index] + (isRightClick and -1 or 1), 0), 99)
changeButton(index)
end
function changeButton(index)
local font_size = BUTTON_PARAMETERS.font_size
local whitespace = " "
if stats[index] > 9 then
font_size = BUTTON_PARAMETERS.font_size * 0.65
whitespace = " "
end
self.editButton({ index = index - 1, label = stats[index] .. whitespace, font_size = font_size })
end
-- formatting of "newStats": {Willpower, Intellect, Fight, Agility}
function updateStats(newStats)
if newStats and #newStats == 4 then
stats = newStats
elseif newStats then
printToAll("Provided new stats are incomplete or incorrectly formatted.", "Red")
return
end
for i = 1, 4 do changeButton(i) end
end

View File

@ -1,83 +1,62 @@
local activeInvestigatorId = nil
-- set true to enable debug logging and show Physics.cast()
local DEBUG = false
function log(message)
if DEBUG then
print(message)
end
end
-- we use this to turn off collision handling until onLoad() is complete
local COLLISION_ENABLED = false
-- builds a function that discards things in searchPostion to discardPostition
function makeDiscardHandlerFor(searchPosition, discardPosition)
return function (_)
local discardItemList = findObjectsAtPosition(searchPosition)
for _, obj in ipairs(discardItemList) do
obj.setPositionSmooth(discardPosition, false, true)
obj.setRotation({0, -90, 0})
end
end
end
-- position offsets relative to mat [x, y, z]
local DRAWN_ENCOUNTER_CARD_OFFSET = {1.365, 0.5, -0.635}
local DRAWN_CHAOS_TOKEN_OFFSET = {-1.55, 0.5, -0.58}
local DISCARD_BUTTON_OFFSETS = {
{-1.365, 0.1, -0.945},
{-0.91, 0.1, -0.945},
{-0.455, 0.1, -0.945},
{0, 0.1, -0.945},
{0.455, 0.1, -0.945},
{0.91, 0.1, -0.945}
}
-- build a discard button at position to discard from searchPosition to discardPosition
-- number must be unique
function makeDiscardButton(position, searchPosition, discardPosition, number)
local handler = makeDiscardHandlerFor(searchPosition, discardPosition)
local handlerName = 'handler' .. number
self.setVar(handlerName, handler)
self.createButton({
label = "Discard",
click_function= handlerName,
function_owner= self,
position = position,
scale = {0.12, 0.12, 0.12},
width = 800,
height = 280,
font_size = 180,
})
end
local PLAY_ZONE_ROTATION = self.getRotation()
function onload(save_state)
local TRASHCAN
local STAT_TRACKER
local RESOURCE_COUNTER
-- global variable so it can be reset by the Clean Up Helper
activeInvestigatorId = "00000"
function onSave() return JSON.encode({zoneID = zoneID, playerColor = PLAYER_COLOR, activeInvestigatorId = activeInvestigatorId}) end
function onLoad(save_state)
self.interactable = DEBUG
DATA_HELPER = getObjectFromGUID('708279')
PLAYER_CARDS = DATA_HELPER.getTable('PLAYER_CARD_DATA')
PLAYER_CARD_TOKEN_OFFSETS = DATA_HELPER.getTable('PLAYER_CARD_TOKEN_OFFSETS')
-- positions of encounter card slots
local encounterSlots = {
{1.365, 0, -0.7},
{0.91, 0, -0.7},
{0.455, 0, -0.7},
{0, 0, -0.7},
{-0.455, 0, -0.7},
{-0.91, 0, -0.7},
}
TRASHCAN = getObjectFromGUID(TRASHCAN_GUID)
STAT_TRACKER = getObjectFromGUID(STAT_TRACKER_GUID)
RESOURCE_COUNTER = getObjectFromGUID(RESOURCE_COUNTER_GUID)
local i = 1
while i <= 6 do
makeDiscardButton(DISCARD_BUTTON_OFFSETS[i], encounterSlots[i], DISCARD_POSITION, i)
i = i + 1
for i = 1, 6 do
makeDiscardButton(DISCARD_BUTTON_OFFSETS[i], {-3.85, 3, 10.38}, i)
end
self.createButton({
label = " ",
click_function = "drawEncountercard",
function_owner = self,
position = {-1.88,0,-0.7},
rotation = {0,-15,0},
width = 170,
height = 255,
font_size = 50
position = {-1.84, 0, -0.65},
rotation = {0, 80, 0},
width = 265,
height = 190
})
self.createButton({
label=" ",
click_function = "drawChaostokenButton",
function_owner = self,
position = {1.84,0.0,-0.74},
position = {1.85, 0, -0.74},
rotation = {0, -45, 0},
width = 125,
height = 125,
font_size = 50
width = 135,
height = 135
})
self.createButton({
@ -93,57 +72,116 @@ function onload(save_state)
local state = JSON.decode(save_state)
if state ~= nil then
if state.playerColor ~= nil then
PLAYER_COLOR = state.playerColor
end
if state.zoneID ~= nil then
zoneID = state.zoneID
Wait.time(checkDeckZoneExists, 30)
else
spawnDeckZone()
end
else
spawnDeckZone()
PLAYER_COLOR = state.playerColor
activeInvestigatorId = state.activeInvestigatorId
end
if getObjectFromGUID(zoneID) == nil then spawnDeckZone() end
COLLISION_ENABLED = true
end
function onSave()
return JSON.encode({ zoneID=zoneID, playerColor=PLAYER_COLOR })
---------------------------------------------------------
-- utility functions
---------------------------------------------------------
function log(message)
if DEBUG then print(message) end
end
function setMessageColor(color)
-- send messages to player who clicked button if no seated player found
function setMessageColor(color)
messageColor = Player[PLAYER_COLOR].seated and PLAYER_COLOR or color
end
-- get the draw deck and discard pile objects
function getDrawDiscardDecks()
drawDeck = nil
discardPile = nil
topCard = nil
function spawnDeckZone()
spawnObject({
position = self.positionToWorld({-1.4, 0, 0.3 }),
scale = {3, 5, 8 },
type = 'ScriptingTrigger',
callback = function (zone) zoneID = zone.getGUID() end,
callback_owner = self,
rotation = self.getRotation()
})
end
local zone = getObjectFromGUID(zoneID)
if zone == nil then return end
function searchArea(origin, size)
return Physics.cast({
origin = origin,
direction = {0, 1, 0},
orientation = PLAY_ZONE_ROTATION,
type = 3,
size = size,
max_distance = 1,
debug = DEBUG
})
end
for i,object in ipairs(zone.getObjects()) do
if object.tag == "Deck" or object.tag == "Card" then
local relativePos = self.positionToLocal(object.getPosition())
if relativePos.z > 0.5 then
discardPile = object
function doNotReady(card) return card.getVar("do_not_ready") or false end
---------------------------------------------------------
-- Discard buttons
---------------------------------------------------------
-- builds a function that discards things in searchPosition to discardPosition
-- stuff on the card/deck will be put into the local trashcan
function makeDiscardHandlerFor(searchPosition, discardPosition)
return function ()
for _, hitObj in ipairs(findObjectsAtPosition(searchPosition)) do
local obj = hitObj.hit_object
if obj.tag == "Deck" or obj.tag == "Card" then
if obj.hasTag("PlayerCard") then
obj.setPositionSmooth(DISCARD_PILE_POSITION, false, true)
obj.setRotation(PLAY_ZONE_ROTATION)
else
if investigator == "Norman Withers" and object.tag == "Card" and not object.is_face_down then
topCard = object
else
drawDeck = object
obj.setPositionSmooth(discardPosition, false, true)
obj.setRotation({0, -90, 0})
end
-- don't touch the table or this playmat itself
elseif obj.guid ~= "4ee1f2" and obj ~= self then
TRASHCAN.putObject(obj)
end
end
end
end
function doUpkeep(obj, color, alt_click)
-- build a discard button to discard from searchPosition to discardPosition (number must be unique)
function makeDiscardButton(position, discardPosition, number)
local searchPosition = {-position[1], position[2], position[3] + 0.32}
local handler = makeDiscardHandlerFor(searchPosition, discardPosition)
local handlerName = 'handler' .. number
self.setVar(handlerName, handler)
self.createButton({
label = "Discard",
click_function = handlerName,
function_owner = self,
position = position,
scale = {0.12, 0.12, 0.12},
width = 800,
height = 280,
font_size = 180
})
end
function findObjectsAtPosition(localPos)
return Physics.cast({
origin = self.positionToWorld(localPos),
direction = {0, 1, 0},
orientation = {0, PLAY_ZONE_ROTATION.y + 90, 0},
type = 3,
size = {3.2, 1, 2},
max_distance = 0,
debug = DEBUG
})
end
---------------------------------------------------------
-- Upkeep button
---------------------------------------------------------
function doUpkeep(_, color, alt_click)
setMessageColor(color)
-- right-click binds to new player color
if alt_click then
PLAYER_COLOR = color
@ -151,139 +189,97 @@ function doUpkeep(obj, color, alt_click)
return
end
setMessageColor(color)
-- unexhaust cards in play zone
local objs = Physics.cast({
origin = PLAY_ZONE_POSITION,
direction = { x=0, y=1, z=0 },
type = 3,
size = PLAY_ZONE_SCALE,
orientation = PLAY_ZONE_ROTATION
})
local y = PLAY_ZONE_ROTATION.y
investigator = nil
local miniId = nil
local forcedLearning = false
for i,v in ipairs(objs) do
-- unexhaust cards in play zone, flip action tokens and find forcedLearning
for _, v in ipairs(searchArea(PLAY_ZONE_POSITION, PLAY_ZONE_SCALE)) do
local obj = v.hit_object
local props = obj.getCustomObject() or {}
if obj.tag == "Card" and not obj.is_face_down and not doNotReady(obj) then
local notes = JSON.decode(obj.getGMNotes()) or {}
local name = obj.getName()
if notes.type == "Investigator" and notes.id ~= nil then
miniId = string.match(notes.id, "%d%d%d%d%d%d-") .. "-m"
end
if notes.type == "Investigator" or props.unique_back then
if string.match(name, "Jenny Barnes") ~= nil then
investigator = "Jenny Barnes"
elseif name == "Patrice Hathaway" then
investigator = name
elseif string.match(name, "Norman Withers") ~= nil then
investigator = "Norman Withers"
end
elseif name == "Forced Learning" then
if notes.id == "08031" then
forcedLearning = true
else
local r = obj.getRotation()
if (r.y - y > 10) or (y - r.y > 10) then
elseif notes.type ~= "Investigator" then
obj.setRotation(PLAY_ZONE_ROTATION)
-- check for cards with 'replenish' in their metadata
if notes.uses ~= nil then
local count = notes.uses[1].count
local replenish = notes.uses[1].replenish
if count and replenish then
replenishTokens(obj, count, replenish)
end
end
elseif obj.getDescription() == "Action Token" then
if obj.is_face_down then obj.flip() end
end
elseif obj.getDescription() == "Action Token" and obj.is_face_down then
obj.flip()
end
end
-- flip investigator mini-card if found
if miniId ~= nil then
objs = getObjects()
for i,obj in ipairs(objs) do
if obj.tag == "Card" then
local notes = JSON.decode(obj.getGMNotes())
if notes ~= nil and notes.type == "Minicard" and notes.id == miniId then
if obj.is_face_down then
obj.flip()
end
goto done
end
end
end
end
::done::
-- flip summoned servitor mini-cards (To-Do: don't flip all of them)
for i, obj in ipairs(getObjects()) do
if obj.tag == "Card" then
if activeInvestigatorId ~= nil then
local miniId = string.match(activeInvestigatorId, "%d%d%d%d%d") .. "-m"
for _, obj in ipairs(getObjects()) do
if obj.tag == "Card" and obj.is_face_down then
local notes = JSON.decode(obj.getGMNotes())
if notes ~= nil and notes.type == "Minicard" and notes.id == "09080-m" then
if obj.is_face_down then
if notes ~= nil and notes.type == "Minicard" and (notes.id == miniId or notes.id == "09080-m") then
obj.flip()
end
end
end
end
-- gain resource
getObjectFromGUID(RESOURCE_COUNTER_GUID).call("add_subtract")
if investigator == "Jenny Barnes" then
getObjectFromGUID(RESOURCE_COUNTER_GUID).call("add_subtract")
-- gain a resource
RESOURCE_COUNTER.call("add_subtract")
-- gain an additional resource for Jenny Barnes
if string.match(activeInvestigatorId, "%d%d%d%d%d") == "02003" then
RESOURCE_COUNTER.call("add_subtract")
printToColor("Gaining 2 resources (Jenny)", messageColor)
end
-- special draw for Patrice Hathaway (shuffle discards if necessary)
if investigator == "Patrice Hathaway" then
patriceDraw()
return
end
-- special draw for Forced Learning
-- draw a card (with handling for Patrice and Forced Learning)
if activeInvestigatorId == "06005" then
if forcedLearning then
forcedLearningDraw()
return
printToColor("Wow, did you really take 'Versatile' to play Patrice with 'Forced Learning'? Choose which draw replacement effect takes priority and draw cards accordingly.", messageColor)
else
local handSize = #Player[PLAYER_COLOR].getHandObjects()
if handSize < 5 then
local cardsToDraw = 5 - handSize
printToColor("Drawing " .. cardsToDraw .. " cards (Patrice)", messageColor)
drawCardsWithReshuffle(cardsToDraw)
end
end
elseif forcedLearning then
printToColor("Drawing 2 cards, discard 1 (Forced Learning)", messageColor)
drawCardsWithReshuffle(2)
else
drawCardsWithReshuffle(1)
end
end
function doDrawOne(obj, color)
-- legacy function for "add draw 1 button"
function doDrawOne(_, color)
setMessageColor(color)
drawCardsWithReshuffle(1)
end
function doNotReady(card)
if card.getVar("do_not_ready") == true then
return true
else
return false
end
end
-- draw X cards (shuffle discards if necessary)
function drawCardsWithReshuffle(numCards)
if type(numCards) ~= "number" then numCards = 1 end
getDrawDiscardDecks()
if investigator == "Norman Withers" then
-- Norman Withers handling
if string.match(activeInvestigatorId, "%d%d%d%d%d") == "08004" then
local harbinger = false
if topCard ~= nil and topCard.getName() == "The Harbinger" then
harbinger = true
else
if drawDeck ~= nil and not drawDeck.is_face_down then
if topCard ~= nil and topCard.getName() == "The Harbinger" then harbinger = true
elseif drawDeck ~= nil and not drawDeck.is_face_down then
local cards = drawDeck.getObjects()
local bottomCard = cards[#cards]
if bottomCard.name == "The Harbinger" then
harbinger = true
end
end
if cards[#cards].name == "The Harbinger" then harbinger = true end
end
if harbinger then
printToColor("The Harbinger is on top of your deck, not drawing cards", messageColor)
return -1
return
end
if topCard ~= nil then
@ -293,13 +289,11 @@ function drawCardsWithReshuffle(numCards)
end
end
local deckSize
local deckSize = 1
if drawDeck == nil then
deckSize = 0
elseif drawDeck.tag == "Deck" then
deckSize = #drawDeck.getObjects()
else
deckSize = 1
end
if deckSize >= numCards then
@ -315,6 +309,29 @@ function drawCardsWithReshuffle(numCards)
printToColor("Take 1 horror (drawing card from empty deck)", messageColor)
end
-- get the draw deck and discard pile objects
function getDrawDiscardDecks()
drawDeck = nil
discardPile = nil
topCard = nil
local zone = getObjectFromGUID(zoneID)
if zone == nil then return end
for _, object in ipairs(zone.getObjects()) do
if object.tag == "Deck" or object.tag == "Card" then
if self.positionToLocal(object.getPosition()).z > 0.5 then
discardPile = object
-- Norman Withers handling
elseif string.match(activeInvestigatorId, "%d%d%d%d%d") == "08004" and object.tag == "Card" and not object.is_face_down then
topCard = object
else
drawDeck = object
end
end
end
end
function drawCards(numCards)
if drawDeck == nil then return end
drawDeck.deal(numCards, PLAYER_COLOR)
@ -328,60 +345,6 @@ function shuffleDiscardIntoDeck()
discardPile = nil
end
function patriceDraw()
local handSize = #Player[PLAYER_COLOR].getHandObjects()
if handSize >= 5 then return end
local cardsToDraw = 5 - handSize
printToColor("Drawing " .. cardsToDraw .. " cards (Patrice)", messageColor)
drawCardsWithReshuffle(cardsToDraw)
end
function forcedLearningDraw()
printToColor("Drawing 2 cards, discard 1 (Forced Learning)", messageColor)
drawCardsWithReshuffle(2)
end
function checkDeckZoneExists()
if getObjectFromGUID(zoneID) ~= nil then return end
spawnDeckZone()
end
function spawnDeckZone()
local pos = self.positionToWorld(DECK_POSITION)
local zoneProps = {
position = pos,
scale = DECK_ZONE_SCALE,
type = 'ScriptingTrigger',
callback = 'zoneCallback',
callback_owner = self,
rotation = self.getRotation()
}
spawnObject(zoneProps)
end
function zoneCallback(zone)
zoneID = zone.getGUID()
end
function findObjectsAtPosition(localPos)
local globalPos = self.positionToWorld(localPos)
local objList = Physics.cast({
origin=globalPos, --Where the cast takes place
direction={0,1,0}, --Which direction it moves (up is shown)
type=2, --Type. 2 is "sphere"
size={2,2,2}, --How large that sphere is
max_distance=1, --How far it moves. Just a little bit
debug=false --If it displays the sphere when casting.
})
local decksAndCards = {}
for _, obj in ipairs(objList) do
if obj.hit_object.tag == "Deck" or obj.hit_object.tag == "Card" then
table.insert(decksAndCards, obj.hit_object)
end
end
return decksAndCards
end
function spawnTokenOn(object, offsets, tokenType)
local tokenPosition = object.positionToWorld(offsets)
spawnToken(tokenPosition, tokenType)
@ -389,32 +352,62 @@ end
-- spawn a group of tokens of the given type on the object
function spawnTokenGroup(object, tokenType, tokenCount)
if (tokenCount < 1 or tokenCount > 12) then
return
end
if (tokenCount < 1 or tokenCount > 12) then return end
local offsets = PLAYER_CARD_TOKEN_OFFSETS[tokenCount]
if offsets == nil then
error("couldn't find offsets for " .. tokenCount .. ' tokens')
end
local i = 0
while i < tokenCount do
local offset = offsets[i + 1]
spawnTokenOn(object, offset, tokenType)
i = i + 1
if offsets == nil then error("couldn't find offsets for " .. tokenCount .. ' tokens') end
for i = 1, tokenCount do
spawnTokenOn(object, offsets[i], tokenType)
end
end
function buildPlayerCardKey(object)
return object.getName() .. ':' .. object.getDescription()
---------------------------------------------------------
-- playmat token spawning
---------------------------------------------------------
-- replenish Tokens for specific cards (like 'Physical Training (4)')
function replenishTokens(card, count, replenish)
local cardPos = card.getPosition()
-- don't continue for cards on your deck (Norman) or in your discard pile
if self.positionToLocal(cardPos).x < -1 then return end
-- get current amount of resource tokens on the card
local search = searchArea(cardPos, { 2.5, 0.5, 3.5 })
local foundTokens = 0
for _, obj in ipairs(search) do
local obj = obj.hit_object
if obj.getCustomObject().image == "http://cloud-3.steamusercontent.com/ugc/1758068501357192910/11DDDC7EF621320962FDCF3AE3211D5EDC3D1573/" then
foundTokens = foundTokens + math.abs(obj.getQuantity())
obj.destruct()
end
end
-- handling Runic Axe upgrade sheet for additional replenish
if card.getName() == "Runic Axe" then
for _, v in ipairs(searchArea(PLAY_ZONE_POSITION, PLAY_ZONE_SCALE)) do
local obj = v.hit_object
if obj.tag == "Card" then
local notes = JSON.decode(obj.getGMNotes()) or {}
if notes ~= nil and notes.id == "09022-c" then
if obj.getVar("markedBoxes")[7] == 3 then replenish = 2 end
break
end
end
end
end
local newCount = foundTokens + replenish
if newCount > count then newCount = count end
spawnTokenGroup(card, "resource", newCount)
end
function getPlayerCardData(object)
return PLAYER_CARDS[buildPlayerCardKey(object)] or PLAYER_CARDS[object.getName()]
return PLAYER_CARDS[object.getName()..':'..object.getDescription()] or PLAYER_CARDS[object.getName()]
end
function shouldSpawnTokens(object)
-- we assume we shouldn't spawn tokens if in doubt, this should
-- only ever happen on load and in that case prevents respawns
-- don't spawn tokens if in doubt, this should only ever happen onLoad and prevents respawns
local spawned = DATA_HELPER.call('getSpawnedPlayerCardGuid', {object.getGUID()})
local hasDataHelperData = getPlayerCardData(object)
local cardMetadata = JSON.decode(object.getGMNotes()) or {}
@ -424,35 +417,55 @@ end
function markSpawned(object)
local saved = DATA_HELPER.call('setSpawnedPlayerCardGuid', {object.getGUID(), true})
if not saved then
error('attempt to mark player card spawned before data loaded')
end
if not saved then error('attempt to mark player card spawned before data loaded') end
end
-- contains position and amount of boxes for the upgradesheets that change uses
-- Alchemical Distillation, Damning Testimony, Living Ink and Hyperphysical Shotcaster
local customizationsTable = {
["09040"] = {5, 2},
["09059"] = {2, 2},
["09079"] = {3, 2},
["09119"] = {6, 4}
}
function spawnTokensFor(object)
local cardMetadata = JSON.decode(object.getGMNotes()) or {}
local token = nil
local type = nil
local token = nil
local tokenCount = 0
if (cardMetadata.uses ~= nil) then
for i, useInfo in ipairs(cardMetadata.uses) do
token = useInfo.token
if cardMetadata.uses ~= nil then
for _, useInfo in ipairs(cardMetadata.uses) do
type = useInfo.type
token = useInfo.token
tokenCount = useInfo.count
if (activeInvestigatorId == "03004" and useInfo.type == "Charge") then
tokenCount = tokenCount + 1
end
-- additional uses for certain customizable cards (by checking the upgradesheets)
if customizationsTable[cardMetadata.id] ~= nil then
for _, obj in ipairs(searchArea(PLAY_ZONE_POSITION, PLAY_ZONE_SCALE)) do
local obj = obj.hit_object
if obj.tag == "Card" then
local notes = JSON.decode(obj.getGMNotes()) or {}
if notes.id == (cardMetadata.id .. "-c") then
local pos = customizationsTable[cardMetadata.id][1]
local boxes = customizationsTable[cardMetadata.id][2]
if obj.getVar("markedBoxes")[pos] == boxes then tokenCount = tokenCount + 2 end
break
end
end
end
end
-- additional charge for Akachi
if activeInvestigatorId == "03004" and type == "Charge" then tokenCount = tokenCount + 1 end
log("Spawning tokens for "..object.getName()..'['..object.getDescription()..']: '..tokenCount.."x "..token)
spawnTokenGroup(object, token, tokenCount)
end
else
local data = getPlayerCardData(object)
if data == nil then
error('attempt to spawn tokens for ' .. object.getName() .. ': no token data')
end
token = data['tokenType']
tokenCount = data['tokenCount']
log(object.getName() .. '[' .. object.getDescription() .. ']' .. ' : ' .. data['tokenType'] .. ' : ' .. data['tokenCount'])
log("Spawning tokens for "..object.getName()..'['..object.getDescription()..']: '..tokenCount.."x "..token)
spawnTokenGroup(object, token, tokenCount)
end
@ -463,16 +476,13 @@ function resetSpawnState()
local zone = getObjectFromGUID(zoneID)
if zone == nil then return end
for i,object in ipairs(zone.getObjects()) do
for _, object in ipairs(zone.getObjects()) do
if object.tag == "Card" then
local guid = object.getGUID()
if guid ~= nil then unmarkSpawned(guid, true) end
unmarkSpawned(object.getGUID(), true)
elseif object.tag == "Deck" then
local cards = object.getObjects()
if (cards ~= nil) then
for i,v in ipairs(cards) do
if v.guid ~= nil then unmarkSpawned(v.guid) end
end
for _, v in ipairs(cards) do
unmarkSpawned(v.guid)
end
end
end
@ -484,64 +494,100 @@ function unmarkSpawned(guid, force)
end
function onCollisionEnter(collision_info)
if (collision_info.collision_object.name == "Card") then
maybeUpdateActiveInvestigator(collision_info.collision_object)
end
if not COLLISION_ENABLED then
return
end
local object = collision_info.collision_object
if not COLLISION_ENABLED then return end
Wait.time(resetSpawnState, 1)
-- anything to the left of this is legal to spawn
local discardSpawnBoundary = self.positionToWorld({-1.2, 0, 0})
local boundaryLocalToCard = object.positionToLocal(discardSpawnBoundary)
if boundaryLocalToCard.x > 0 then
log('not checking for token spawn, boundary relative is ' .. boundaryLocalToCard.x)
return
end
if not object.is_face_down and shouldSpawnTokens(object) then
local object = collision_info.collision_object
-- only continue for cards
if object.name ~= "Card" and object.name ~= "CardCustom" then return end
maybeUpdateActiveInvestigator(object)
-- don't spawn tokens for cards in discard pile / threat area
local localpos = self.positionToLocal(object.getPosition())
if localpos.x < -0.7 or localpos.z < -0.3 then
log('Not spawning tokens, relative coordinates are x: ' .. localpos.x .. ' z: ' .. localpos.z)
elseif not object.is_face_down and shouldSpawnTokens(object) then
spawnTokensFor(object)
end
end
---------------------------------------------------------
-- investigator ID grabbing and stat tracker
---------------------------------------------------------
function maybeUpdateActiveInvestigator(card)
local cardMetadata = JSON.decode(card.getGMNotes()) or {}
if (cardMetadata.type == "Investigator") then
activeInvestigatorId = cardMetadata.id
updateStatToken(willpowerTokenGuid, cardMetadata.willpowerIcons)
updateStatToken(intellectTokenGuid, cardMetadata.intellectIcons)
updateStatToken(combatTokenGuid, cardMetadata.combatIcons)
updateStatToken(agilityTokenGuid, cardMetadata.agilityIcons)
local notes = JSON.decode(card.getGMNotes())
if notes ~= nil and notes.type == "Investigator" and notes.id ~= activeInvestigatorId then
activeInvestigatorId = notes.id
STAT_TRACKER.call("updateStats", {notes.willpowerIcons, notes.intellectIcons, notes.combatIcons, notes.agilityIcons})
-- change state of action tokens
local search = searchArea(self.positionToWorld({-1.1, 0.05, -0.27}), {4, 1, 1})
local small_token = nil
local state_table = {
["Guardian"] = 1,
["Seeker"] = 2,
["Rogue"] = 3,
["Mystic"] = 4,
["Survivor"] = 5,
["Neutral"] = 6
}
for _, obj in ipairs(search) do
local obj = obj.hit_object
if obj.getDescription() == "Action Token" and obj.getStateId() > 0 then
if obj.getScale().x < 0.4 then
small_token = obj
else
setObjectState(obj, state_table[notes.class])
end
end
end
function updateStatToken(tokenGuid, val)
local statToken = getObjectFromGUID(tokenGuid)
if (statToken == nil) then
return
-- update the small token with special action for certain investigators
-- Ursula Downs: Investigate action
if activeInvestigatorId == "04002" then
setObjectState(small_token, 8)
-- Daisy Walker (only for normal front, not parallel): Tome action
elseif activeInvestigatorId == "01002" or activeInvestigatorId == "01502" or activeInvestigatorId == "01002-pb" then
setObjectState(small_token, 9)
-- Tony Morgan: Engage/Fight action
elseif activeInvestigatorId == "06003" then
setObjectState(small_token, 10)
-- Finn Edwards: Evade action
elseif activeInvestigatorId == "04003" then
setObjectState(small_token, 11)
-- Bob Jenkins: Play Item action
elseif activeInvestigatorId == "08016" then
setObjectState(small_token, 14)
else
setObjectState(small_token, state_table[notes.class])
end
statToken.call("reset_val")
for i = 1, val do
statToken.call("add_subtract", { alt_click = false })
end
end
-- functions delegated to Global
function drawChaostokenButton(object, player, isRightClick)
-- local toPosition = self.positionToWorld(DRAWN_CHAOS_TOKEN_OFFSET)
function setObjectState(obj, stateId)
if obj.getStateId() ~= stateId then obj.setState(stateId) end
end
---------------------------------------------------------
-- calls to 'Global' / functions for calls from outside
---------------------------------------------------------
function drawChaostokenButton(_, _, isRightClick)
Global.call("drawChaostoken", {self, DRAWN_CHAOS_TOKEN_OFFSET, isRightClick})
end
function drawEncountercard(object, player, isRightClick)
local toPosition = self.positionToWorld(DRAWN_ENCOUNTER_CARD_OFFSET)
Global.call("drawEncountercard", {toPosition, self.getRotation(), isRightClick})
function drawEncountercard(_, _, isRightClick)
Global.call("drawEncountercard", {self.positionToWorld(DRAWN_ENCOUNTER_CARD_OFFSET), self.getRotation(), isRightClick})
end
function spawnToken(position, tokenType)
Global.call('spawnToken', {position, tokenType})
Global.call('spawnToken', {position, tokenType, PLAY_ZONE_ROTATION})
end
-- called by custom data helpers to add player card data
---@param args table Contains only one entry, the GUID of the custom data helper
function updatePlayerCards(args)
local custom_data_helper = getObjectFromGUID(args[1])
data_player_cards = custom_data_helper.getTable("PLAYER_CARD_DATA")

View File

@ -1,132 +0,0 @@
MIN_VALUE = -99
MAX_VALUE = 999
function onload(saved_data)
light_mode = false
val = 0
if saved_data ~= "" then
local loaded_data = JSON.decode(saved_data)
light_mode = loaded_data[1]
val = loaded_data[2]
end
createAll()
end
function updateSave()
local data_to_save = {light_mode, val}
saved_data = JSON.encode(data_to_save)
self.script_state = saved_data
end
function createAll()
s_color = {0.5, 0.5, 0.5, 95}
if light_mode then
f_color = {1,1,1,95}
else
f_color = {0,0,0,100}
end
self.createButton({
label=tostring(val),
click_function="add_subtract",
function_owner=self,
position={0,0.05,0},
height=600,
width=1000,
alignment = 3,
scale={x=1.5, y=1.5, z=1.5},
font_size=600,
font_color=f_color,
color={0,0,0,0}
})
if light_mode then
lightButtonText = "[ Set dark ]"
else
lightButtonText = "[ Set light ]"
end
end
function removeAll()
self.removeInput(0)
self.removeInput(1)
self.removeButton(0)
self.removeButton(1)
self.removeButton(2)
end
function reloadAll()
removeAll()
createAll()
updateSave()
end
function swap_fcolor(_obj, _color, alt_click)
light_mode = not light_mode
reloadAll()
end
function swap_align(_obj, _color, alt_click)
center_mode = not center_mode
reloadAll()
end
function editName(_obj, _string, value)
self.setName(value)
setTooltips()
end
function add_subtract(_obj, _color, alt_click)
mod = alt_click and -1 or 1
new_value = math.min(math.max(val + mod, MIN_VALUE), MAX_VALUE)
if val ~= new_value then
val = new_value
updateVal()
updateSave()
end
end
function updateVal()
self.editButton({
index = 0,
label = tostring(val),
})
end
function reset_val()
val = 0
updateVal()
updateSave()
end
function setTooltips()
self.editInput({
index = 0,
value = self.getName(),
tooltip = ttText
})
self.editButton({
index = 0,
value = tostring(val),
tooltip = ttText
})
end
function null()
end
function keepSample(_obj, _string, value)
reloadAll()
end