From 63dc59e2a43f39d8723c2bfe8db7a47785d969a3 Mon Sep 17 00:00:00 2001 From: 96LawDawg <76912527+96LawDawg@users.noreply.github.com> Date: Tue, 28 Jan 2025 09:30:22 -0600 Subject: [PATCH] Add support for resetProperties (#2447) --- client/js/jsonedit.js | 25 + client/js/widgets/widget.js | 13 +- library/tutorials/Functions - RESET/0.json | 1103 +++++++++++++++++ .../Functions - RESET/assets/-738418506_3024 | Bin 0 -> 3024 bytes .../Functions - RESET/assets/1042468064_1967 | 18 + .../Functions - RESET/assets/606927958_4524 | Bin 0 -> 4524 bytes 6 files changed, 1158 insertions(+), 1 deletion(-) create mode 100644 library/tutorials/Functions - RESET/0.json create mode 100644 library/tutorials/Functions - RESET/assets/-738418506_3024 create mode 100644 library/tutorials/Functions - RESET/assets/1042468064_1967 create mode 100644 library/tutorials/Functions - RESET/assets/606927958_4524 diff --git a/client/js/jsonedit.js b/client/js/jsonedit.js index 19e34bd300..6fbc013388 100644 --- a/client/js/jsonedit.js +++ b/client/js/jsonedit.js @@ -1107,6 +1107,7 @@ function jeAddCommands() { jeAddRoutineOperationCommands('MOVE', { count: 1, face: null, from: null, to: null, fillTo: null, collection: 'DEFAULT' }); jeAddRoutineOperationCommands('MOVEXY', { count: 1, face: null, from: null, x: 0, y: 0, snapToGrid: true, resetOwner: true }); jeAddRoutineOperationCommands('RECALL', { owned: true, inHolder: true, holder: null, excludeCollection: null }); + jeAddRoutineOperationCommands('RESET', { property: 'resetProperties' }); jeAddRoutineOperationCommands('ROTATE', { count: 1, angle: 90, mode: 'add', holder: null, collection: 'DEFAULT' }); jeAddRoutineOperationCommands('SCORE', { mode: 'set', property: 'score', seats: null, round: null, value: null }); jeAddRoutineOperationCommands('SELECT', { type: 'all', property: 'parent', relation: '==', value: null, max: 999999, collection: 'DEFAULT', mode: 'set', source: 'all', sortBy: '###SEE jeAddRoutineOperation###'}); @@ -1149,6 +1150,15 @@ function jeAddCommands() { jeAddLimitCommand('maxX'); jeAddLimitCommand('maxY'); + // Default values computed dynamically. + jeAddResetPropertiesCommand('parent'); + jeAddResetPropertiesCommand('x'); + jeAddResetPropertiesCommand('y'); + jeAddResetPropertiesCommand('rotation'); + jeAddResetPropertiesCommand('activeFace'); + jeAddResetPropertiesCommand('scale'); + jeAddResetPropertiesCommand('display'); + jeAddFieldCommand('text', 'subtitle|title|text', ''); jeAddFieldCommand('label', 'checkbox|choose|color|number|palette|select|string|switch', ''); jeAddFieldCommand('value', 'checkbox|choose|color|number|palette|select|string|switch', ''); @@ -1484,6 +1494,21 @@ function jeAddNumberCommand(name, key, callback) { }); } +function jeAddResetPropertiesCommand(key) { + jeCommands.push({ + id: 'rProp_' + key, + name: key, + context: '^[^ ]* ↦ resetProperties', + show: _=>typeof jeStateNow.resetProperties == "object" && jeStateNow.resetProperties !== null && !(key in jeStateNow.resetProperties), + call: async function() { + const w = widgets.get(jeStateNow.id); + jeStateNow.resetProperties[key] = '###SELECT ME###'; + let rProp = w.get(key); + jeSetAndSelect(rProp); + } + }); +} + function jeAddWidgetPropertyCommands(object, widgetBase) { for(const property in object.defaults) if(property != 'typeClasses' && !property.match(/^c[0-9]{2}$/)) diff --git a/client/js/widgets/widget.js b/client/js/widgets/widget.js index 3de28be127..d293a12d91 100644 --- a/client/js/widgets/widget.js +++ b/client/js/widgets/widget.js @@ -90,7 +90,8 @@ export class Widget extends StateManaged { gameStartRoutine: null, hotkey: null, - animatePropertyChange: [] + animatePropertyChange: [], + resetProperties: {}, }); this.domElement.timer = false @@ -1620,6 +1621,16 @@ export class Widget extends StateManaged { } } + if (a.func == 'RESET') { + setDefaults(a, { property: 'resetProperties' }); + for(const widget of widgets.values()) + for(const [ key, value ] of Object.entries(widget.get(a.property) || {})) + await widget.set(key, value); + if (jeRoutineLogging) { + jeLoggingRoutineOperationSummary(`Reset properties for widgets with property '${a.property}'`); + } + } + if(a.func == 'ROTATE') { setDefaults(a, { count: 1, angle: 90, mode: 'add', collection: 'DEFAULT' }); if(a.count === 'all') diff --git a/library/tutorials/Functions - RESET/0.json b/library/tutorials/Functions - RESET/0.json new file mode 100644 index 0000000000..cb695d9546 --- /dev/null +++ b/library/tutorials/Functions - RESET/0.json @@ -0,0 +1,1103 @@ +{ + "_meta": { + "version": 17, + "info": { + "name": "Functions - RESET", + "image": "/assets/1042468064_1967", + "rules": "", + "bgg": "", + "year": "", + "mode": "Tutorial", + "time": "0", + "attribution": "", + "lastUpdate": 1737065890550, + "showName": false, + "skill": "", + "description": "", + "similarImage": "", + "similarName": "", + "similarDesigner": "", + "similarAwards": "", + "ruleText": "", + "helpText": "", + "variantImage": "", + "variant": "", + "language": "en-US", + "players": "1" + } + }, + "fzoqD": { + "type": "deck", + "id": "fzoqD", + "x": 12, + "y": 41, + "cardTypes": { + "T 1J": { + "image": "/i/cards-default/1J.svg", + "suit": "T", + "suitColor": "🃏", + "suitAlt": "5J", + "rank": "J1", + "rankA": "J1", + "rankFixed": "J1 T" + }, + "T 2J": { + "image": "/i/cards-default/2J.svg", + "suit": "T", + "suitColor": "🃏", + "suitAlt": "5J", + "rank": "J2", + "rankA": "J2", + "rankFixed": "J2 T" + }, + "C 01": { + "image": "/i/cards-default/AC.svg", + "suit": "C", + "suitColor": "♣", + "suitAlt": "1♣", + "rank": "01", + "rankA": "5A", + "rankFixed": "01 C" + }, + "C 02": { + "image": "/i/cards-default/2C.svg", + "suit": "C", + "suitColor": "♣", + "suitAlt": "1♣", + "rank": "02", + "rankA": "02", + "rankFixed": "02 C" + }, + "C 03": { + "image": "/i/cards-default/3C.svg", + "suit": "C", + "suitColor": "♣", + "suitAlt": "1♣", + "rank": "03", + "rankA": "03", + "rankFixed": "03 C" + }, + "C 04": { + "image": "/i/cards-default/4C.svg", + "suit": "C", + "suitColor": "♣", + "suitAlt": "1♣", + "rank": "04", + "rankA": "04", + "rankFixed": "04 C" + }, + "C 05": { + "image": "/i/cards-default/5C.svg", + "suit": "C", + "suitColor": "♣", + "suitAlt": "1♣", + "rank": "05", + "rankA": "05", + "rankFixed": "05 C" + }, + "C 06": { + "image": "/i/cards-default/6C.svg", + "suit": "C", + "suitColor": "♣", + "suitAlt": "1♣", + "rank": "06", + "rankA": "06", + "rankFixed": "06 C" + }, + "C 07": { + "image": "/i/cards-default/7C.svg", + "suit": "C", + "suitColor": "♣", + "suitAlt": "1♣", + "rank": "07", + "rankA": "07", + "rankFixed": "07 C" + }, + "C 08": { + "image": "/i/cards-default/8C.svg", + "suit": "C", + "suitColor": "♣", + "suitAlt": "1♣", + "rank": "08", + "rankA": "08", + "rankFixed": "08 C" + }, + "C 09": { + "image": "/i/cards-default/9C.svg", + "suit": "C", + "suitColor": "♣", + "suitAlt": "1♣", + "rank": "09", + "rankA": "09", + "rankFixed": "09 C" + }, + "C 10": { + "image": "/i/cards-default/TC.svg", + "suit": "C", + "suitColor": "♣", + "suitAlt": "1♣", + "rank": "10", + "rankA": "10", + "rankFixed": "10 C" + }, + "C 2J": { + "image": "/i/cards-default/JC.svg", + "suit": "C", + "suitColor": "♣", + "suitAlt": "1♣", + "rank": "2J", + "rankA": "2J", + "rankFixed": "2J C" + }, + "C 3Q": { + "image": "/i/cards-default/QC.svg", + "suit": "C", + "suitColor": "♣", + "suitAlt": "1♣", + "rank": "3Q", + "rankA": "3Q", + "rankFixed": "3Q C" + }, + "C 4K": { + "image": "/i/cards-default/KC.svg", + "suit": "C", + "suitColor": "♣", + "suitAlt": "1♣", + "rank": "4K", + "rankA": "4K", + "rankFixed": "4K C" + }, + "D 01": { + "image": "/i/cards-default/AD.svg", + "suit": "D", + "suitColor": "♦", + "suitAlt": "4♦", + "rank": "01", + "rankA": "5A", + "rankFixed": "01 D" + }, + "D 02": { + "image": "/i/cards-default/2D.svg", + "suit": "D", + "suitColor": "♦", + "suitAlt": "4♦", + "rank": "02", + "rankA": "02", + "rankFixed": "02 D" + }, + "D 03": { + "image": "/i/cards-default/3D.svg", + "suit": "D", + "suitColor": "♦", + "suitAlt": "4♦", + "rank": "03", + "rankA": "03", + "rankFixed": "03 D" + }, + "D 04": { + "image": "/i/cards-default/4D.svg", + "suit": "D", + "suitColor": "♦", + "suitAlt": "4♦", + "rank": "04", + "rankA": "04", + "rankFixed": "04 D" + }, + "D 05": { + "image": "/i/cards-default/5D.svg", + "suit": "D", + "suitColor": "♦", + "suitAlt": "4♦", + "rank": "05", + "rankA": "05", + "rankFixed": "05 D" + }, + "D 06": { + "image": "/i/cards-default/6D.svg", + "suit": "D", + "suitColor": "♦", + "suitAlt": "4♦", + "rank": "06", + "rankA": "06", + "rankFixed": "06 D" + }, + "D 07": { + "image": "/i/cards-default/7D.svg", + "suit": "D", + "suitColor": "♦", + "suitAlt": "4♦", + "rank": "07", + "rankA": "07", + "rankFixed": "07 D" + }, + "D 08": { + "image": "/i/cards-default/8D.svg", + "suit": "D", + "suitColor": "♦", + "suitAlt": "4♦", + "rank": "08", + "rankA": "08", + "rankFixed": "08 D" + }, + "D 09": { + "image": "/i/cards-default/9D.svg", + "suit": "D", + "suitColor": "♦", + "suitAlt": "4♦", + "rank": "09", + "rankA": "09", + "rankFixed": "09 D" + }, + "D 10": { + "image": "/i/cards-default/TD.svg", + "suit": "D", + "suitColor": "♦", + "suitAlt": "4♦", + "rank": "10", + "rankA": "10", + "rankFixed": "10 D" + }, + "D 2J": { + "image": "/i/cards-default/JD.svg", + "suit": "D", + "suitColor": "♦", + "suitAlt": "4♦", + "rank": "2J", + "rankA": "2J", + "rankFixed": "2J D" + }, + "D 3Q": { + "image": "/i/cards-default/QD.svg", + "suit": "D", + "suitColor": "♦", + "suitAlt": "4♦", + "rank": "3Q", + "rankA": "3Q", + "rankFixed": "3Q D" + }, + "D 4K": { + "image": "/i/cards-default/KD.svg", + "suit": "D", + "suitColor": "♦", + "suitAlt": "4♦", + "rank": "4K", + "rankA": "4K", + "rankFixed": "4K D" + }, + "H 01": { + "image": "/i/cards-default/AH.svg", + "suit": "H", + "suitColor": "♥", + "suitAlt": "2♥", + "rank": "01", + "rankA": "5A", + "rankFixed": "01 H" + }, + "H 02": { + "image": "/i/cards-default/2H.svg", + "suit": "H", + "suitColor": "♥", + "suitAlt": "2♥", + "rank": "02", + "rankA": "02", + "rankFixed": "02 H" + }, + "H 03": { + "image": "/i/cards-default/3H.svg", + "suit": "H", + "suitColor": "♥", + "suitAlt": "2♥", + "rank": "03", + "rankA": "03", + "rankFixed": "03 H" + }, + "H 04": { + "image": "/i/cards-default/4H.svg", + "suit": "H", + "suitColor": "♥", + "suitAlt": "2♥", + "rank": "04", + "rankA": "04", + "rankFixed": "04 H" + }, + "H 05": { + "image": "/i/cards-default/5H.svg", + "suit": "H", + "suitColor": "♥", + "suitAlt": "2♥", + "rank": "05", + "rankA": "05", + "rankFixed": "05 H" + }, + "H 06": { + "image": "/i/cards-default/6H.svg", + "suit": "H", + "suitColor": "♥", + "suitAlt": "2♥", + "rank": "06", + "rankA": "06", + "rankFixed": "06 H" + }, + "H 07": { + "image": "/i/cards-default/7H.svg", + "suit": "H", + "suitColor": "♥", + "suitAlt": "2♥", + "rank": "07", + "rankA": "07", + "rankFixed": "07 H" + }, + "H 08": { + "image": "/i/cards-default/8H.svg", + "suit": "H", + "suitColor": "♥", + "suitAlt": "2♥", + "rank": "08", + "rankA": "08", + "rankFixed": "08 H" + }, + "H 09": { + "image": "/i/cards-default/9H.svg", + "suit": "H", + "suitColor": "♥", + "suitAlt": "2♥", + "rank": "09", + "rankA": "09", + "rankFixed": "09 H" + }, + "H 10": { + "image": "/i/cards-default/TH.svg", + "suit": "H", + "suitColor": "♥", + "suitAlt": "2♥", + "rank": "10", + "rankA": "10", + "rankFixed": "10 H" + }, + "H 2J": { + "image": "/i/cards-default/JH.svg", + "suit": "H", + "suitColor": "♥", + "suitAlt": "2♥", + "rank": "2J", + "rankA": "2J", + "rankFixed": "2J H" + }, + "H 3Q": { + "image": "/i/cards-default/QH.svg", + "suit": "H", + "suitColor": "♥", + "suitAlt": "2♥", + "rank": "3Q", + "rankA": "3Q", + "rankFixed": "3Q H" + }, + "H 4K": { + "image": "/i/cards-default/KH.svg", + "suit": "H", + "suitColor": "♥", + "suitAlt": "2♥", + "rank": "4K", + "rankA": "4K", + "rankFixed": "4K H" + }, + "S 01": { + "image": "/i/cards-default/AS.svg", + "suit": "S", + "suitColor": "♠", + "suitAlt": "3♠", + "rank": "01", + "rankA": "5A", + "rankFixed": "01 S" + }, + "S 02": { + "image": "/i/cards-default/2S.svg", + "suit": "S", + "suitColor": "♠", + "suitAlt": "3♠", + "rank": "02", + "rankA": "02", + "rankFixed": "02 S" + }, + "S 03": { + "image": "/i/cards-default/3S.svg", + "suit": "S", + "suitColor": "♠", + "suitAlt": "3♠", + "rank": "03", + "rankA": "03", + "rankFixed": "03 S" + }, + "S 04": { + "image": "/i/cards-default/4S.svg", + "suit": "S", + "suitColor": "♠", + "suitAlt": "3♠", + "rank": "04", + "rankA": "04", + "rankFixed": "04 S" + }, + "S 05": { + "image": "/i/cards-default/5S.svg", + "suit": "S", + "suitColor": "♠", + "suitAlt": "3♠", + "rank": "05", + "rankA": "05", + "rankFixed": "05 S" + }, + "S 06": { + "image": "/i/cards-default/6S.svg", + "suit": "S", + "suitColor": "♠", + "suitAlt": "3♠", + "rank": "06", + "rankA": "06", + "rankFixed": "06 S" + }, + "S 07": { + "image": "/i/cards-default/7S.svg", + "suit": "S", + "suitColor": "♠", + "suitAlt": "3♠", + "rank": "07", + "rankA": "07", + "rankFixed": "07 S" + }, + "S 08": { + "image": "/i/cards-default/8S.svg", + "suit": "S", + "suitColor": "♠", + "suitAlt": "3♠", + "rank": "08", + "rankA": "08", + "rankFixed": "08 S" + }, + "S 09": { + "image": "/i/cards-default/9S.svg", + "suit": "S", + "suitColor": "♠", + "suitAlt": "3♠", + "rank": "09", + "rankA": "09", + "rankFixed": "09 S" + }, + "S 10": { + "image": "/i/cards-default/TS.svg", + "suit": "S", + "suitColor": "♠", + "suitAlt": "3♠", + "rank": "10", + "rankA": "10", + "rankFixed": "10 S" + }, + "S 2J": { + "image": "/i/cards-default/JS.svg", + "suit": "S", + "suitColor": "♠", + "suitAlt": "3♠", + "rank": "2J", + "rankA": "2J", + "rankFixed": "2J S" + }, + "S 3Q": { + "image": "/i/cards-default/QS.svg", + "suit": "S", + "suitColor": "♠", + "suitAlt": "3♠", + "rank": "3Q", + "rankA": "3Q", + "rankFixed": "3Q S" + }, + "S 4K": { + "image": "/i/cards-default/KS.svg", + "suit": "S", + "suitColor": "♠", + "suitAlt": "3♠", + "rank": "4K", + "rankA": "4K", + "rankFixed": "4K S" + } + }, + "faceTemplates": [ + { + "border": false, + "radius": false, + "objects": [ + { + "type": "image", + "x": 0, + "y": 0, + "width": 103, + "height": 160, + "color": "transparent", + "value": "/i/cards-default/2B.svg" + } + ] + }, + { + "border": false, + "radius": false, + "objects": [ + { + "type": "image", + "x": 0, + "y": 0, + "width": 103, + "height": 160, + "color": "transparent", + "dynamicProperties": { + "value": "image" + } + } + ] + } + ], + "parent": "cardHolder", + "cardDefaults": { + "button3Reset": { + "parent": "cardHolder", + "activeFace": 0 + } + } + }, + "cardHolder": { + "type": "holder", + "id": "cardHolder", + "x": 840, + "y": 269, + "z": 128, + "dropTarget": { + "type": "card" + } + }, + "header": { + "id": "header", + "x": 400, + "y": -2, + "width": 800, + "height": 60, + "z": 74, + "movable": false, + "movableInEdit": false, + "css": "font-size: 60px;text-align:center", + "text": "Functions: RESET" + }, + "mainText": { + "id": "mainText", + "x": 100, + "y": 100, + "width": 1405, + "height": 150, + "layer": -3, + "z": 124, + "css": "font-size: 25px; ", + "text": "RESET is a simple function that only accepts one parameter: `property`. The default value is `resetProperties` and it should be an object with key:value pairs such as {x:0, y:100}. When used, RESET looks for every widget in the room with the property specified in the parameter and changes the widget properties to match what is in the object. Basically, this resets widgets to a default state that you designate. The JSON Editor can also help you easily create `resetProperties` for your widgets.", + "movable": false + }, + "meeple": { + "id": "meeple", + "x": 86, + "y": 832, + "width": 66.5, + "height": 70, + "z": 10080, + "color": "#1f5ca6", + "css": { + "border-radius": "45% 65% 70% 30%/ 45% 50% 20% 20%", + "transition": "linear 1s" + }, + "image": "i/game-pieces/3D/Meeple-3D.svg", + "resetProperties": { + "x": 68, + "y": 342, + "rotation": 0, + "scale": 1 + }, + "svgReplaces": { + "#primaryColor": "color", + "#borderColor": "borderColor", + "#borderWidth": "borderWidth" + }, + "borderColor": "#000000", + "borderWidth": 1, + "clickRoutine": [ + { + "func": "SET", + "collection": "thisButton", + "property": "rotation", + "relation": "+", + "value": 45 + } + ], + "rotation": 540, + "scale": 2 + }, + "wood": { + "id": "wood", + "x": 268, + "y": 828, + "width": 26, + "z": 10031, + "color": "#1f5ca6", + "image": "i/game-pieces/3D/Road240-3D.svg", + "resetProperties": { + "x": 244, + "y": 327, + "rotation": 0 + }, + "svgReplaces": { + "#primaryColor": "color", + "#borderColor": "borderColor", + "#borderWidth": "borderWidth" + }, + "borderColor": "#000000", + "borderWidth": 1, + "clickRoutine": [ + { + "func": "SET", + "collection": "thisButton", + "property": "rotation", + "relation": "+", + "value": 45 + } + ], + "rotation": 90, + "css": { + "transition": "linear 1s" + } + }, + "button1": { + "type": "button", + "id": "button1", + "x": 151, + "y": 450, + "z": 8, + "text": "RESET", + "clickRoutine": [ + { + "func": "RESET" + } + ] + }, + "button2": { + "type": "button", + "id": "button2", + "x": 502, + "y": 450, + "z": 9, + "css": { + "background": "red" + }, + "text": "RESET", + "clickRoutine": [ + { + "func": "RESET", + "property": "redReset" + } + ] + }, + "button3": { + "type": "button", + "id": "button3", + "x": 939, + "y": 450, + "z": 9, + "text": "RESET", + "clickRoutine": [ + { + "func": "RESET", + "property": "button3Reset" + } + ], + "css": { + "background": "green" + } + }, + "button1Text": { + "id": "button1Text", + "x": 60, + "y": 600, + "width": 306, + "z": 185, + "movable": false, + "text": "Look at the meeple and stick below in the JSON editor and note the `resetProperties`. The grey pawn and house also have resetProperties. The button above updates the properties on the widget to match the `resetProperties`. So they will move, rotate, and scale as needed. A css transition is applied to the widgets to clearly demonstrate the effect." + }, + "button2Text": { + "id": "button2Text", + "x": 410, + "y": 600, + "width": 300, + "z": 121, + "movable": false, + "text": "The button above applies the RESET function to a different custom property, redReset. The gray pawn and house are updated by both the blue and red buttons, but for different properties. In the case of the pawn and house, only the color property is changed." + }, + "pawn": { + "id": "pawn", + "x": 449, + "y": 832, + "width": 50.4, + "height": 90, + "z": 10032, + "color": "#808080", + "css": { + "border-radius": "40% 40% 50% 50%/ 80% 80% 10% 10%", + "transition": "linear 1s" + }, + "image": "i/game-pieces/3D/Pawn-3D.svg", + "resetProperties": { + "x": 460, + "y": 337 + }, + "svgReplaces": { + "#primaryColor": "color", + "#borderColor": "borderColor", + "#borderWidth": "borderWidth" + }, + "borderColor": "black", + "borderWidth": 1, + "redReset": { + "color": "red" + } + }, + "house": { + "id": "house", + "x": 596, + "y": 848, + "width": 60, + "height": 60, + "z": 10033, + "color": "#808080", + "css": { + "border-radius": "26% 74% 46% 54%/ 50% 55% 45% 50%", + "transition": "linear 1s" + }, + "image": "/i/game-pieces/3D/House-3D.svg", + "resetProperties": { + "x": 588, + "y": 358 + }, + "svgReplaces": { + "#primaryColor": "color", + "#secondaryColor": "secondaryColor", + "#borderColor": "borderColor", + "#borderWidth": "borderWidth" + }, + "borderColor": "#000000", + "borderWidth": 2, + "redReset": { + "color": "red" + } + }, + "button3Text": { + "id": "button3Text", + "x": 746, + "y": 600, + "width": 500, + "z": 9732, + "movable": false, + "text": "The cards, cubes, and marbles all use RESET for the `parent` property. The cards have the reset property on the `cardDefaults` and the Ace has an additional reset directly on it. The cards and cubes are moved in an order not controllable by the game designer. Use a sort, shuffle or whatever else is appropriate. Order of the properties in the reset property matters. For example, the marbles are being parented to the seat in a particular location. But the yellow marble has its parent set after the x/y are set, so it is not in the location you might expect. " + }, + "zdvo": { + "deck": "fzoqD", + "type": "card", + "cardType": "C 01", + "id": "zdvo", + "z": 10942, + "x": 1014, + "y": 830, + "activeFace": 1, + "button3Reset": { + "x": 718, + "y": 271 + } + }, + "371o": { + "deck": "fzoqD", + "type": "card", + "cardType": "C 02", + "id": "371o", + "z": 10941, + "activeFace": 1, + "x": 964, + "y": 805 + }, + "zw4e": { + "deck": "fzoqD", + "type": "card", + "cardType": "C 03", + "id": "zw4e", + "z": 10938, + "activeFace": 1, + "x": 914, + "y": 780 + }, + "c3av": { + "deck": "fzoqD", + "type": "card", + "cardType": "C 04", + "id": "c3av", + "z": 10937, + "activeFace": 1, + "x": 864, + "y": 755 + }, + "cube1": { + "id": "cube1", + "width": 36, + "height": 40, + "z": 10077, + "color": "orange", + "css": "border-radius: 50%/35%;", + "image": "/i/game-pieces/3D/Cube-3D.svg", + "svgReplaces": { + "#primaryColor": "color", + "#secondaryColor": "secondaryColor", + "#borderColor": "borderColor", + "#borderWidth": "borderWidth" + }, + "borderColor": "white", + "borderWidth": 1, + "secondaryColor": "black", + "button3Reset": { + "parent": "cubeHolder" + }, + "x": 852, + "y": 947 + }, + "cubeHolder": { + "type": "holder", + "id": "cubeHolder", + "x": 964, + "y": 269, + "z": 129, + "width": 196, + "height": 40, + "dropTarget": {}, + "stackOffsetX": 40, + "dropOffsetX": 0, + "dropOffsetY": 0 + }, + "seat1": { + "type": "seat", + "id": "seat1", + "x": 980, + "y": 347, + "color": "#1f5ca6", + "player": "Test Player" + }, + "cube2": { + "inheritFrom": { + "cube1": "!parent" + }, + "id": "cube2", + "x": 778, + "y": 947, + "color": "purple", + "button3Reset": { + "parent": "cubeHolder" + }, + "z": 10075 + }, + "cube3": { + "inheritFrom": { + "cube1": "!parent" + }, + "id": "cube3", + "x": 926, + "y": 947, + "color": "yellow", + "button3Reset": { + "parent": "cubeHolder" + }, + "z": 10071 + }, + "cube4": { + "inheritFrom": { + "cube1": "!parent" + }, + "id": "cube4", + "x": 889, + "y": 947, + "color": "green", + "button3Reset": { + "parent": "cubeHolder" + }, + "z": 10070 + }, + "cube5": { + "inheritFrom": { + "cube1": "!parent" + }, + "id": "cube5", + "x": 815, + "y": 947, + "color": "blue", + "button3Reset": { + "parent": "cubeHolder" + }, + "z": 10076 + }, + "marble1": { + "id": "marble1", + "x": 1120, + "y": 755, + "width": 35, + "height": 35, + "z": 10089, + "color": "orange", + "css": "border-radius: 50%;", + "image": "/i/game-pieces/3D/Marble-3D.svg", + "svgReplaces": { + "#primaryColor": "color", + "#secondaryColor": "secondaryColor", + "#borderColor": "borderColor", + "#borderWidth": "borderWidth" + }, + "borderColor": "#ffffff", + "borderWidth": 1, + "secondaryColor": "#000000", + "button3Reset": { + "parent": "seat1", + "x": -23, + "y": 50 + } + }, + "marble2": { + "id": "marble2", + "width": 35, + "height": 35, + "z": 10090, + "color": "purple", + "css": "border-radius: 50%;", + "image": "/i/game-pieces/3D/Marble-3D.svg", + "svgReplaces": { + "#primaryColor": "color", + "#secondaryColor": "secondaryColor", + "#borderColor": "borderColor", + "#borderWidth": "borderWidth" + }, + "borderColor": "#ffffff", + "borderWidth": 1, + "secondaryColor": "#000000", + "y": 806, + "button3Reset": { + "parent": "seat1", + "x": 17, + "y": 50 + }, + "x": 1120 + }, + "marble3": { + "id": "marble3", + "x": 1120, + "y": 906, + "width": 35, + "height": 35, + "z": 10092, + "color": "yellow", + "css": "border-radius: 50%;", + "image": "/i/game-pieces/3D/Marble-3D.svg", + "svgReplaces": { + "#primaryColor": "color", + "#secondaryColor": "secondaryColor", + "#borderColor": "borderColor", + "#borderWidth": "borderWidth" + }, + "borderColor": "#ffffff", + "borderWidth": 1, + "secondaryColor": "#000000", + "button3Reset": { + "x": 56, + "y": 50, + "parent": "seat1" + } + }, + "marble4": { + "id": "marble4", + "x": 1120, + "y": 957, + "width": 35, + "height": 35, + "z": 10093, + "color": "green", + "css": "border-radius: 50%;", + "image": "/i/game-pieces/3D/Marble-3D.svg", + "svgReplaces": { + "#primaryColor": "color", + "#secondaryColor": "secondaryColor", + "#borderColor": "borderColor", + "#borderWidth": "borderWidth" + }, + "borderColor": "#ffffff", + "borderWidth": 1, + "secondaryColor": "#000000", + "button3Reset": { + "parent": "seat1", + "x": 96, + "y": 50 + } + }, + "marble5": { + "id": "marble5", + "x": 1120, + "y": 856, + "width": 35, + "height": 35, + "z": 10091, + "color": "blue", + "css": "border-radius: 50%;", + "image": "/i/game-pieces/3D/Marble-3D.svg", + "svgReplaces": { + "#primaryColor": "color", + "#secondaryColor": "secondaryColor", + "#borderColor": "borderColor", + "#borderWidth": "borderWidth" + }, + "borderColor": "#ffffff", + "borderWidth": 1, + "secondaryColor": "#000000", + "button3Reset": { + "parent": "seat1", + "x": 135, + "y": 50 + } + }, + "json1": { + "id": "json1", + "x": 1327, + "y": 329, + "width": 200, + "height": 200, + "image": "/assets/-738418506_3024", + "z": 10094, + "movable": false + }, + "json2": { + "id": "json2", + "x": 1291, + "y": 686, + "width": 300, + "height": 300, + "image": "/assets/606927958_4524", + "movable": false + }, + "JSONText2": { + "id": "JSONText2", + "x": 1290, + "y": 527, + "width": 306, + "z": 185, + "movable": false, + "text": "While the cursor is in the `resetProperties` property, you can click on any of these available buttons for common properties. The current value of that property will be added, so having the widget where you want it to reset to is a good idea. But you can also enter any property and customize the value." + }, + "JSONText1": { + "id": "JSONText1", + "x": 1290, + "y": 254, + "width": 306, + "z": 185, + "movable": false, + "text": "To use the JSON Editor, put the cursor in the properties area of the widget that is not a routine and look near the bottom of the available buttons for `resetProperties`." + } +} \ No newline at end of file diff --git a/library/tutorials/Functions - RESET/assets/-738418506_3024 b/library/tutorials/Functions - RESET/assets/-738418506_3024 new file mode 100644 index 0000000000000000000000000000000000000000..5fe24976968326e9347df8fbc39bb4d911251d81 GIT binary patch literal 3024 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 U_wp3mjxxg`i<5Apnj--J0q4LhVE_OC literal 0 HcmV?d00001 diff --git a/library/tutorials/Functions - RESET/assets/1042468064_1967 b/library/tutorials/Functions - RESET/assets/1042468064_1967 new file mode 100644 index 0000000000..0463b9c4cc --- /dev/null +++ b/library/tutorials/Functions - RESET/assets/1042468064_1967 @@ -0,0 +1,18 @@ + + Buttons Blue + + + + Functions: + + RESET + + + + + \ No newline at end of file diff --git a/library/tutorials/Functions - RESET/assets/606927958_4524 b/library/tutorials/Functions - RESET/assets/606927958_4524 new file mode 100644 index 0000000000000000000000000000000000000000..b5bbc0d9dd82706850afdbf579dd4ccb0a28a4c3 GIT binary patch literal 4524 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