For an overview of how cards and decks work, read the information below and check out a YouTube tutorial at https://www.youtube.com/watch?v=xmdMTWuRO-E&t=2371s (and also later in the video at https://www.youtube.com/watch?v=xmdMTWuRO-E&t=3377s).
Cards
Cards are a type of widget with specific behavior and default settings designed to simulate different types of cards. Most of the properties of card widgets are defined in their deck, and every card must belong to a deck. Cards are not visible in edit mode, but they are selectable in the JSON editor. In the JSON editor (or by using SET) a property can be set on the cards directly, and that property will override any properties set in cardDefaults or cardTypes.
Although one normally thinks of cards as having two faces, a front and a back, cards in VirtualTableTop can have an arbitrary number of faces.
Decks
Click to see tutorial
A deck consists of a number of cards, each of which is an instance of a cardType. A deck may have multiple instances of a given cardType (for example, a standard 54-card deck might have two identical jokers); it may also have no instances of a given cardType (for example, the default deck contains cardTypes defining jokers, but the deck itself contains no jokers, so contains no cards of that cardType).
A particular property of an individual card in a deck takes its value from the card widget if it is defined there. Otherwise, if it is defined in the card's cardType, it takes its value from that definition. Otherwise, if it is defined in the deck's cardDefaults, it takes its value from that definition. Finally, if it is not defined in any of those places, it takes a default value assigned by the system. In addition, properties specific to a given face may be defined in the properties object of the faceTemplate describing a given face; these become the default for that property when that face is active, and will override properties set in cardDefaults but not properties set in cardTypes or directly on the card.
Decks appear in edit mode as a circle with a pile of cards icon and a number inside it. The number reflects the number of cards actually available in the room for that deck. For example, the default deck shows 52, because the jokers are not in the deck but are included as one of the cardTypes.
A portion of the JSON for the default deck is shown below. The various elements are described after that.
"cardDefaults": {
"width": 103,
"height": 160
},
"cardTypes": {
...
"C 01": {
"image": "/i/cards-default/AC.svg",
"suit": "C",
"suitColor": "♣",
"suitAlt": "1♣",
"rank": "01",
"rankA": "5A",
"rankFixed": "01 C"
},
...
},
"faceTemplates": [
{
"border": false,
"radius": false,
"objects": [
{
"type": "image",
"x": 0,
"y": 0,
"width": 103,
"height": 160,
"value": "/i/cards-default/2B.svg",
"color": "transparent"
}
]
},
{
"border": false,
"radius": false,
"objects": [
{
"type": "image",
"x": 0,
"y": 0,
"width": 103,
"height": 160,
"color": "transparent",
"dynamicProperties": {
"value": "image"
}
}
]
}
]
cardDefaults
cardDefaults contain default properties that apply to every card in a deck. Usually the width and height of every card in a deck is the same, so they would normally be set in cardDefaults. (Note that the cardDefaults given here do not actually appear in the JSON for the default deck, as these are the default values for the width and height parameters.)
cardDefaults is where you would put a clickRoutine that you want to have happen every time a card from the deck is clicked. Also, you can modify the attributes of piles by putting an onPileCreation property here.
cardTypes
cardTypes contains properties that only apply to a specific type of card (e.g. an Ace of Clubs, shown). The values of properties for each cardType that are entered in the Deck Editor are stored in cardTypes. Properties set in cardTypes override properties set in cardDefaults.
Each cardType will often contain specific images. For example, a dynamicProperties reference in a faceTemplates object may be "nest": "/assets/-1177660470_1251". "Nest" is the variable and that assets reference is the link to an image uploaded into VTT. In a different card, the nest might reference a difference asset image. Another (more complicated, but easier to adjust once completed) method is demonstrated in the Demo Library in the Card Images with CSS Classes room. Using the methods demonstrated there, you could do something like "nest": "bigNest" and "nest": "littleNest". In that case bigNest and littleNest would have the asset links on the card deck and changes to the image would be applied across all the cards.
faceTemplates: text, image, icon
faceTemplates is used to define the layout for each face of the cards.
The objects within each face are the components that are displayed on the face from the bottom up in the order listed. The object types can be text, image, icon, or html. The first three are discussed here and html types are discussed in the next section.
Most decks have playing cards with identical back sides. In the default deck the back side is the only object in the top face. It is given a type of image (because it is an image), and a value that refers to the url of the image if desired. The x and y given are relative to the card, so an image object with a y of 50 would appear 50 pixels below the top of the card. For images, the color is what will show through transparent portions of the image, and for text it is the text color. Background color would need to be set in css in either cardDefaults, or in faceTemplates (in the same spot where border and radius are set in the default deck).
The second faceTemplate in the default deck specifies that the face of each card will have a different image, by using dynamicProperties. For this faceTemplate, "dynamicProperties":{"value":"image"} says use the value of the card's "image" property (stored in cardTypes) for the object's "value" property.
Each card in the default deck has two faces, so there are two faceTemplates defined. In general, however, a faceTemplate can be an array of objects, one for each face. Each object contains an array , "objects". Each element of the "objects" array specifies a property of the corresponding face. A property is the same for all cards if the value is set directly in the object element. dynamicProperties is used to map card properties to object properties. Each key of dynamicProperties specifies the name of an object property to provide. The value of that key is the name of the property of the card to use. Consider the following faceTemplates specification:
"faceTemplates": [
{
"objects": [
{
"type": "image",
"color": "blue",
"width": 103,
"height": 160
}
],
"border": 4
},
{
"objects": [
{
"type": "icon",
"x": 25,
"y": 55,
"size": 50,
"dynamicProperties": {
"value": "iconShape",
"color": "iconColor"
}
},
{
"type": "text",
"x": 0,
"y": 0,
"fontSize": 20,
"textAlign": "center",
"width": 103,
"dynamicProperties": {
"value": "city",
"color": "textColor"
}
}
],
"border": 1,
"radius": 8
}
]
This provides face templates for a deck in which each card contains two faces. The first face is blue for all cards, with the given width and height, and a 4 pixel border. The contents of the second face depend on the card. The second face has two elements on it. The first is an icon whose shape and color is set on each card using the dynamicProperties values for iconShape and iconColor. It is positioned approximately in the middle of the card and is size 50. The second element on the face is text with fontSize 20, positioned at the upper left corner of the card (at (0,0)) and centered. The text on each card is given by the city property of the card and the color of the text is the textColor property of the card.
Example cardTypes that would work with this:
"cardTypes": {
"newYork": {
"city": "New York",
"textColor": "red",
"iconShape": "various-artists/infinity",
"iconColor": "red"
},
"london": {
"city": "London",
"textColor": "green",
"iconShape": "heat",
"iconColor": "blue"
}
},
Note: If using css in a faceTemplate object, you must use the simple (string) form of css and not the object form.
In addition to defining face objects, faceTemplates can set properties linked to the active face through a "properties" object. Properties defined in the "properties" object of a face become the default for that property when that face is active (overriding properties sent in cardDefaults but not properties set in cardTypes or directly on the card).
In the following often requested example from the default deck, a properties parameter has been added that enlarges only the face up side since there is no point in enlarging the back of the card.
"faceTemplates": [
{
"objects": [
{
"type": "image",
"width": 103,
"height": 160,
"value": "/i/cards-default/2B.svg"
}
]
},
{
"objects": [
{
"type": "image",
"width": 103,
"height": 160,
"dynamicProperties": {
"value": "image"
}
}
],
"properties": {
"enlarge": 2
}
}
]
Additional properties that will not be displayed on the cards can be added to each cardType directly. For example, it is possible to create a changeRoutine or clickRoutine.
faceTemplates: html
The faceTemplate examples discussed in the previous section objects consisting of either image or text. A third available category is html. This allows for styled text, inline embedded images, and generally most anything that is allowed in html. Here is an example where html is the 3rd element on this particular object. Additional examples are in the Decks tutorial, HTML variant.
"faceTemplates": [
{
...
},
{
"objects": [
{
"type": "image",
...
},
{
"type": "text",
...
},
{
"type": "html",
"css": {
"body": { "display": "flex"; "flex-direction": "column" },
".desc": { "flex": 1 },
".footer": { "font-size": "12px" },
}
"x": 0,
"y": 60,
"width": 140,
"height": 64,
"value": "<div class=desc>${PROPERTY description}</div><div class=footer>${PROPERTY summary}</div>"
},
]
}
]
Editing decks and cards
Some of the information below is duplicated from the Edit-Mode discussion about the Properties section of the Menu.
You can start a new deck by uploading cards (or picking from some pre-defined suits) by using the Properties button in the JSON Editor.
Once a deck is created, decks and cards can be edited in two different ways.
-
The most powerful way of editing decks and cards is by editing the JSON directly. While in the JSON Editor, on the Menu to the right, click on "{} JSON". This method allows you to edit the JSON directly, which has the advantage that you can zero in immediately on what to change, and gives you the ability to add and create properties whereas with the other method, you can only change existing properties. Note, if you delete the
cardTypeentry while a widget with thatcardTypestill exists, the widget does not get automatically deleted. It remains in the room as a card with a transparent front until you refresh. You can adjust the number of cards actually available in the room by placing the cursor on the cardType for that specific card and looking for the blue buttons on the right to "add card n" or "remove card n" (where n will be the new number of cards of that type). -
The other way to edit cards is by using the Properties button. While in the JSON Editor, on the Menu to the right, click on "Properties" (or the icon that looks like 3 parallel lines with knobs). Then select a card or deck from the room.
a. If the widget selected is a card, you see the card properties, which can be changed directly. It also shows information about the card type. There you can immediately add or remove the count of that type of card in the room or click on the edit button below the card to make additional changes to the details from the card's faceTemplate.
b. If the widget selected is a deck, you see all of the card types. There are buttons to add or remove one of every card type of each button press. Or you can individually add or remove cards or edit data from the cards' faceTemplate. The deck view also shows how each individual layer from the faceTemplate looks for each card face. Finally, you can also view and edit the cardDefaults from this deck view as well.
(Note: Some changes in the deck manager are instant and some require you to push the apply changes button. Instant: adding or removing cards using +/- buttons; card default properties, and card properties if viewing a single card and not the whole deck. Button approval: card layers and edits to cardTypes properties on individual cards.
Quick Links
Home
1. Basics
2. Developer Documentation
- Widgets
- Functions, automation, and routines
- Dynamic Expressions and using variables
- Math, string, array, color, JSON functions
- Cards and Decks
- Editing JSON
- Using CSS
- Fonts and Symbols
3. Available Resources
- Publicly available games
- Tutorials
- Demonstration Features
- Useful Code Snippets
- Useful Global CSS Snippets
4. Usage Guidelines and Copyrights
5. Other Technical Information
- Download Repository
- Using GitHub and creating Pull Requests
- Internals Overview
- Testing with TestCafé
- URL-addressing rooms
- Using Docker containers
- Config.json file