feat(bgm): derive definition names from role.type

A definition is identified by role.type and named role.type.lang
(package.lang for packages). Code blocks declare it via role= on the
info string; real files by their filename. Blocks and files without a
matching role.type are ignored. file= still overrides the auto-name.

Relative asset and $variants paths now resolve against the markdown
file's directory (baseDir) rather than the virtual name. Same role.type
with different ids groups under one name; duplicate type#id still
errors. Migrate fixtures and example games to role=.
This commit is contained in:
2026-08-10 16:36:57 +08:00
parent 23332ab786
commit 13b3eaed78
12 changed files with 211 additions and 173 deletions
+4 -11
View File
@@ -4,8 +4,7 @@ The base game's 24 landscape tiles, laid out on a table with a draw pile and a
grid of placed tiles. Each tile is a single `110×110` image (AX), sized to a
standard `45×45` mm square.
```yaml file=carcassonne.yaml
role: package
```yaml role=package
id: carcassonne
title: Carcassonne
designer: Klaus-Jürgen Wrede
@@ -21,9 +20,7 @@ One `tile` part per distinct tile type (AX). All tiles share the same square
face image and a uniform size; the `$variants` CSV expands them into the 24
tile parts.
```yaml file=tiles.yaml
role: part
type: tile
```yaml role=part.tile
face: ./20AE_Base_Game_C2_Tile_A.png
size: [45, 45, 3]
fillet: 1
@@ -65,10 +62,8 @@ A table with a draw pile on the left and an `11×11` grid of placed tiles in the
middle. The grid routes each tile to its `col,row` cell, spaced `45` mm apart
so tiles sit edge to edge.
```yaml file=board.yaml
type: board
```yaml role=surface.board
id: board
role: surface
size: [600, 600]
layout:
- route: /draw
@@ -215,9 +210,7 @@ string,string,number,number,number
Start with the full tile supply on the draw pile (`carcassonne:tile` expands to
every tile of that type), then seed the grid with a few opening tiles.
```yaml file=main.yaml
role: setup
type: game
```yaml role=setup.game
id: main
surfaces:
- board#board