Code frameworks
Schemas de Framework
Declare entradas, ações, valores derivados, Frames, conteúdo e Frameworks filhos para um tipo de Element.
Um arquivo de Framework
Cada arquivo em schemas/ declara um Framework. As páginas de referência fazem o Keeper do início rápido crescer. Agora ele tem uma escolha de Calling, um valor derivado Guard, um preset pronto, uma seção e um Lamp filho.
manifest/project.json
schemas/keeper.json
schemas/lamp.json
rules/keeper.ts
rules/lamp.ts
rules/hurt.ts
rules/heal.ts
rules/guard.ts
layouts/keeper.json
layouts/lamp.json
scenarios/new-keeper.json
scenarios/heal.json
scenarios/new-lamp.jsonCampos principais
| Campo | Obrigatório | Significado |
|---|---|---|
| id | Sim | O id único do Framework. O manifesto e os cenários usam esse id. |
| name | Sim | O nome de exibição. |
| elementType | Sim | O que ele cria: character para personagens jogáveis, item para objetos, spell para magias. Tipos personalizados são permitidos. |
| constructor | Sim | O caminho do arquivo de regras que cria um novo Element. |
| inputs | Não | O que o jogador informa ao criar um Element. Cada chave corresponde a um parâmetro do constructor. |
| actions | Não | Coisas que um Element pode fazer. Cada uma tem um id, um nome e um arquivo de regras. |
| ledgerFunctions | Não | Valores derivados. Cada um aponta para um campo salvo e tem um arquivo de regras. |
| frames | Sim | De um a dezesseis Frames. Exatamente um tem default definido como true. |
| sections | Não | Agrupa as entradas em etapas do assistente de criação. |
| content | Não | Presets prontos. Cada um tem um id, um nome e valores de entrada. |
| childFrameworks | Não | Liga o nome de um espaço filho a outro Framework do mesmo jogo. |
Em um GAME, o Framework de entrada no manifesto precisa ser um personagem jogável.
The entry framework must be a character constructor.Entradas
Uma entrada personaliza um parâmetro do constructor, e sua chave deve ter o mesmo nome do parâmetro. A maioria das entradas só precisa de um label. As outras chaves limitam o que o jogador pode informar.
"inputs": {
"name": { "label": "Name" },
"max_hp": {
"label": "Maximum HP",
"description": "How much damage a Keeper can take.",
"defaultValue": 10,
"min": 1,
"max": 40
},
"calling": {
"label": "Calling",
"options": ["Guard", "Scout"],
"defaultValue": "Guard"
},
"lamp": { "label": "Lamp", "defaultValue": "lamp", "hidden": true }
},- Linhas 8-14 min e max limitam um número. Um cenário ou predefinição fora dos limites falha.
- Linhas 15-19 options dá uma lista fixa de escolhas. O padrão deve ser uma delas.
- Linha 20 Uma entrada hidden guarda um valor que o jogador nunca vê. Aqui ela liga o Lamp filho.
schemas/keeper.json
{
"id": "keeper",
"name": "Keeper",
"elementType": "character",
"constructor": "rules/keeper.ts",
"inputs": {
"name": { "label": "Name" },
"max_hp": {
"label": "Maximum HP",
"description": "How much damage a Keeper can take.",
"defaultValue": 10,
"min": 1,
"max": 40
},
"calling": {
"label": "Calling",
"options": ["Guard", "Scout"],
"defaultValue": "Guard"
},
"lamp": { "label": "Lamp", "defaultValue": "lamp", "hidden": true }
},
"childFrameworks": { "lamp": "lamp" },
"sections": [
{
"id": "basics",
"title": "Basics",
"inputs": ["name", "max_hp", "calling", "lamp"]
}
],
"actions": [
{ "id": "hurt", "name": "Take damage", "source": "rules/hurt.ts" },
{ "id": "heal", "name": "Heal", "source": "rules/heal.ts" }
],
"ledgerFunctions": [
{
"id": "guard",
"name": "Guard",
"field": "guard",
"source": "rules/guard.ts"
}
],
"frames": [
{ "id": "sheet", "source": "layouts/keeper.json", "default": true }
],
"content": [
{
"id": "mira-scout",
"name": "Mira the Scout",
"parameters": {
"name": "Mira",
"max_hp": 8,
"calling": "Scout",
"lamp": "lamp"
}
}
]
}| Chave | Significado |
|---|---|
| label | O texto mostrado ao jogador. |
| description | Texto de ajuda, com até 1024 caracteres. |
| defaultValue | O valor usado quando o jogador não mexe na entrada. |
| options | Uma lista fixa de 2 a 128 escolhas de texto, cada uma com até 128 caracteres. O padrão deve ser uma delas. |
| optionLabels | Rótulos das opções para o jogador. O valor salvo continua sendo a opção. |
| min, max | Limites para um número. min não pode ser maior que max. |
| minLength, maxLength | Limites para o tamanho de um texto. |
| required | Defina como false para deixar o jogador livre para não preencher a entrada. |
| hidden | Tira a entrada do assistente. Uma entrada oculta precisa de um defaultValue. |
| visibleWhen | Mostra a entrada só enquanto uma condição sobre outras entradas for verdadeira. |
Um padrão que não é uma das opções é recusado.
{
"calling": {
"label": "Calling",
"options": ["Guard", "Scout"],
"defaultValue": "Mage"
}
}Default for calling must be one of its options ("Guard", "Scout").Cenários e presets também precisam respeitar os limites.
Parameter max_hp 99 is not between 1 and 40.Uma entrada oculta sem padrão falha com:
Input name is hidden, so it must declare a defaultValue.Ações e funções de ledger
Cada ação tem um id, um nome e um arquivo de código. Cada função de ledger tem os mesmos itens, mais um campo. O campo é o valor salvo que a função deriva, e deve ser um campo escalar que o constructor retorna. Uma função de ledger lê valores e retorna o valor derivado. Ela nunca escreve.
"ledgerFunctions": [
{
"id": "guard",
"name": "Guard",
"field": "guard",
"source": "rules/guard.ts"
}
],- Linhas 36-39 id e name identificam a função, field é o valor guardado que ela deriva e source é o seu arquivo de regras.
function base_guard(calling: string): number {
return calling === "Guard" ? 3 : 1;
}
export function guard(currentValue: number, self: ElementRef): number {
const calling: string = element.var(self, "calling") as string;
return base_guard(calling);
}- Linhas 1-3 Uma função auxiliar. Ela não tem export, e a função do ledger a chama pelo nome.
- Linha 5 Uma função do ledger recebe seu valor atual e o Element.
- Linha 6 Leia os valores guardados com element.var.
- Linha 7 Retorne o valor derivado.
Ledger function must target an existing scalar field.Os ids devem ser únicos dentro de um Framework. Ações e funções de ledger compartilham um único conjunto de ids.
Duplicate semantic identity or source path.Duas funções de ledger podem compartilhar um arquivo de origem. Uma ação e uma função de ledger não podem:
action source does not match its owner contractEntradas de ação
As entradas de uma ação são os parâmetros da sua função. A assinatura as declara, e o esquema pode acrescentar um registo para cada uma. Cada entrada é um número, um texto ou um valor verdadeiro/falso.
O jogador é solicitado a fornecer cada entrada num diálogo quando usa o botão. O diálogo nomeia uma entrada pelo nome do seu parâmetro, a menos que o registo lhe dê um rótulo. Um registo também pode dar uma descrição e um valor padrão. Uma entrada numérica pode ter um mínimo e um máximo. Uma entrada de texto pode ter uma lista de opções ou opções de uma tabela. O diálogo mostra tudo, e o servidor recusa um valor fora dos limites ou das opções. Um botão não pode fornecer um valor. Dê a cada parâmetro um nome que o jogador consiga ler: roll, não r.
{
"id": "check_lore",
"name": "Lore check",
"source": "rules/check-lore.ts",
"inputs": { "roll": { "label": "Roll", "min": 1, "max": 100 } }
}- Linha 24 O registo da entrada da rolagem. O diálogo mostra o rótulo e o servidor impõe o mínimo e o máximo.
Um mínimo e um máximo não impedem um número com casas decimais. Se a regra precisa de um número inteiro, ela própria verifica, e um passo do cenário comprova. Um passo do cenário fora dos limites é recusado.
export function check_lore(self: ElementRef, roll: number): void {
if (math.floor(roll) === roll) {
const lore: number = element.var(self, "lore") as number;
ledger.set(self, "last_target", lore);
ledger.set(self, "last_roll", roll);
}
}- Linha 1 A rolagem é uma entrada que o jogador digita.
- Linha 2 Ignore um número com casas decimais. Os limites da entrada já o mantêm entre 1 e 100.
- Linhas 4-5 Escreva o alvo e a rolagem.
Uma entrada de texto também pode oferecer uma lista de escolhas de uma tabela do livro de regras. A página Tabelas do livro de regras mostra como.
Uma entrada de texto pode, em vez disso, escolher pelo nome um dos campos armazenados do Framework, com uma lista fields. A página Escrevendo regras mostra uma ação que a usa.
Uma entrada numérica pode pedir ao servidor que a jogue. Adicione uma chave roll com uma expressão de dados, como "roll": "1d100" ou "roll": "2d6+1". O diálogo mostra então um botão Jogar no lugar de um campo onde o jogador digita. O servidor joga e o diálogo mostra o total, que o jogador não pode alterar. Só um parâmetro numérico pode ser jogado. O compilador recusa um roll junto com um defaultValue e recusa uma expressão de dados que o servidor não aceita.
Uma entrada jogada é gasta uma só vez: a ação usa a jogada quando é executada, e uma nova jogada anula as anteriores não gastas dessa entrada. Uma jogada fica ligada à sua campanha e expira após 15 minutos. A página Layouts e fichas mostra o que a mesa vê.
Linha de registo de uma ação
Uma ação pode publicar uma linha de resultado no registo da mesa. Adicione um modelo de registo à entrada da ação no esquema, por exemplo "log": "{name} takes {amount} damage, defense {defense}". O servidor preenche cada marcador {name} como texto simples depois de a ação ser guardada. Um navegador nunca envia a linha.
Um marcador pode nomear uma entrada da ação, ou um campo numérico, de texto ou verdadeiro/falso do mesmo Framework. O compilador recusa uma entrada oculta, um campo de saúde (hp, current_hp, hit_points, temp_hp, current_health, max_health, hitPoints, e os campos de saúde e de condição do bloco de combate), um nome que não existe, um modelo com mais de 200 caracteres, mais de 16 marcadores, uma chaveta solta e um carácter de controlo. Quando uma entrada e um campo partilham o nome, ganha a entrada. Os valores são os de depois da ação, por isso um campo que a ação escreveu mostra o valor novo. Um campo calculado não é recalculado, por isso mostra o valor que tinha antes da ação.
Um jogador que age no seu próprio personagem vê a linha na mesma audiência das suas jogadas de dados: todos, só ele, ou ele e os GMs. Em qualquer outro caso, incluindo um GM a agir em qualquer personagem, a linha chega apenas aos membros da campanha que podem ler esse personagem. Se a audiência for todos mas um membro não puder ler o personagem, a linha vai como mensagem privada para os membros que podem. A mesa mostra a linha com a etiqueta Jogo, para que ninguém a confunda com a mensagem de um jogador.
Presets de conteúdo
Um preset é um conjunto nomeado de valores de entrada, como um personagem pronto. O Fabled verifica cada preset como um cenário, então todo valor deve caber na sua entrada. Um jogo pode ter até 512 presets por Framework.
"content": [
{
"id": "mira-scout",
"name": "Mira the Scout",
"parameters": {
"name": "Mira",
"max_hp": 8,
"calling": "Scout",
"lamp": "lamp"
}
}
]- Linhas 47-48 Uma predefinição tem um id e um name.
- Linhas 49-54 Os valores de entrada que a predefinição preenche. Eles devem caber nos limites da entrada.
Seções
As seções agrupam as entradas em etapas do assistente de criação. Quando um Framework declara seções, toda entrada deve estar em uma delas, inclusive as ocultas.
"sections": [
{
"id": "basics",
"title": "Basics",
"inputs": ["name", "max_hp", "calling", "lamp"]
}
],- Linhas 25-27 Uma seção tem um id, um title e as entradas que ela mostra. Toda entrada deve estar em uma seção.
Input lamp is not assigned to any section.Frameworks filhos
Um Framework filho é uma parte de um Element maior, como o Lamp que um Keeper carrega. O filho tem seu próprio schema, constructor, Frame e cenário.
"childFrameworks": { "lamp": "lamp" },- Linha 22 Liga o espaço filho lamp ao Framework com o id lamp.
{
"id": "lamp",
"name": "Lamp",
"elementType": "item",
"constructor": "rules/lamp.ts",
"inputs": {
"name": { "label": "Name" },
"oil": { "label": "Oil", "defaultValue": 5 }
},
"frames": [{ "id": "card", "source": "layouts/lamp.json", "default": true }]
}- Linhas 6-9 As entradas do filho. Um filho também precisa de um name.
- Linha 10 O filho tem o seu próprio Frame.
O pai liga o nome de um espaço ao id de um Framework em childFrameworks. Uma entrada oculta guarda a referência. O constructor retorna as entradas do filho junto com seus próprios valores.
export function construct(
name: string,
max_hp: number,
calling: string,
lamp: FrameworkRef,
): {
values: { name: string; max_hp: number; hp: number; calling: string; guard: number };
children: { lamp: { framework: FrameworkRef; params: { name: string; oil: number } } };
} {
return {
values: { name: name, max_hp: max_hp, hp: max_hp, calling: calling, guard: 0 },
children: { lamp: { framework: lamp, params: { name: "Lantern", oil: 5 } } },
};
}- Linha 5 lamp é um FrameworkRef. A plataforma transforma o id do Framework da entrada em um.
- Linhas 6-9 O tipo de retorno lista os valores guardados e os espaços filhos.
- Linha 11 Os valores iniciais do Keeper.
- Linha 12 O espaço filho: qual Framework criar e quais entradas dar a ele.
Todo Framework, filhos incluídos, deve retornar um name.
must define the required 'name' value, normally as a string constructor field.Um espaço que aponta para um Framework fora do jogo falha com:
Invalid child Framework constraint: lamp.Campos avançados
| Campo | Finalidade |
|---|---|
| lists | Conteúdo que um personagem ganha durante o jogo. |
| contentChoices | Pontos de escolha em que o jogador escolhe um item de um Framework de conteúdo. |
| slots | Seletores para escolhas repetíveis. |
| pools | Pools compartilhados dos quais as entradas de número são tiradas. |
| modifiers | Números que a plataforma deriva dos efeitos do conteúdo. |
| effects | Como um Framework de conteúdo nomeia um modificador e uma quantidade. |
| levelling | Subir ou descer um personagem um nível depois da criação. |
| rebuild | O que uma reconstrução faz com o estado de jogo, como uma mudança de nível. |
| combat | Os papéis que as ferramentas de combate da mesa leem. |
| catalogue | Registros de conteúdo guardados fora do código-fonte e adicionados em blocos. |
| tables | Tabelas de dados compartilhadas. |
| playReads | Valores derivados que a mesa lê de atributos guardados. |
| rulesAttacks | Ataques que todo personagem tem. |
| optionsFrom | Pega as opções de uma entrada de outra fonte. |
| rich, richText | Marca uma entrada de texto como texto formatado. |

