The brief was a tool in Foundry that generates everything on a click and injects
it as a new dungeon. Previously the module could only stage a delve authored at
the desk, and the only way in was a console command — an API with a button glued
on, which is why it looked like nothing was there.
The ⛏ button now opens a form (theme, areas, depth, heroes, deadliness, density,
greed, clock, ending, seed, and whether to build maps and roll encounters), and
Raise the dungeon builds the lot in about five seconds:
• a folder per document type, named for the dungeon
• one scene per area, walls and lighting placed, via the VANITY Forge
• encounter actors, foldered rather than scattered across the world
• a JournalEntry — GM truth, a page per area, the ending — which is the
adventure, and is written to be read cold
The journal is the deliverable. Scenes without it are a pile of maps.
Generating is cheap, so removing had to be. Every document DELVE creates is
stamped with a dungeonId, and a 🗑 button lists what it built and deletes one
dungeon entirely — confirming with exact counts first, and never deleting the
scene the GM is standing in. Colour is not an identifier: it is a Color object,
and a GM may recolour a folder.
Verified live: two dungeons raised from the form and the API, then one removed
cleanly at -3 scenes, -10 actors, -1 journal, -3 folders with nothing else
touched.
Co-Authored-By: Claude Opus 5 <noreply@anthropic.com>
63 lines
2.6 KiB
Handlebars
63 lines
2.6 KiB
Handlebars
<div class="delve-forge">
|
|
<p class="hint">Generates a complete dungeon — fiction, areas, maps, encounters, hoards and a
|
|
journal you can read cold — and drops it into this world in one folder.</p>
|
|
|
|
<div class="delve-grid">
|
|
<label>Theme
|
|
<select name="theme">
|
|
{{#each themes}}<option value="{{this}}" {{#if (eq this ../v.theme)}}selected{{/if}}>{{this}}</option>{{/each}}
|
|
</select>
|
|
</label>
|
|
<label>Areas
|
|
<input type="number" name="areas" value="{{v.areas}}" min="3" max="12" step="1">
|
|
</label>
|
|
<label>Depth
|
|
<select name="depth">
|
|
{{#each picks.depth}}<option value="{{this}}" {{#if (eq this ../v.depth)}}selected{{/if}}>{{this}}</option>{{/each}}
|
|
</select>
|
|
</label>
|
|
<label>Heroes
|
|
<select name="party">
|
|
{{#each picks.party}}<option value="{{this}}" {{#if (eq this ../v.party)}}selected{{/if}}>{{this}}</option>{{/each}}
|
|
</select>
|
|
</label>
|
|
<label>Deadliness
|
|
<select name="deadliness">
|
|
{{#each picks.deadliness}}<option value="{{this}}" {{#if (eq this ../v.deadliness)}}selected{{/if}}>{{this}}</option>{{/each}}
|
|
</select>
|
|
</label>
|
|
<label>Density
|
|
<select name="density">
|
|
{{#each picks.density}}<option value="{{this}}" {{#if (eq this ../v.density)}}selected{{/if}}>{{this}}</option>{{/each}}
|
|
</select>
|
|
</label>
|
|
<label>Greed
|
|
<select name="greed">
|
|
{{#each picks.greed}}<option value="{{this}}" {{#if (eq this ../v.greed)}}selected{{/if}}>{{this}}</option>{{/each}}
|
|
</select>
|
|
</label>
|
|
<label>Clock
|
|
<select name="clock">
|
|
{{#each picks.clock}}<option value="{{this}}" {{#if (eq this ../v.clock)}}selected{{/if}}>{{this}}</option>{{/each}}
|
|
</select>
|
|
</label>
|
|
<label>Ending
|
|
<select name="ending">
|
|
{{#each picks.ending}}<option value="{{this}}" {{#if (eq this ../v.ending)}}selected{{/if}}>{{this}}</option>{{/each}}
|
|
</select>
|
|
</label>
|
|
<label>Seed <span class="sub">blank = random</span>
|
|
<input type="text" name="seed" value="{{v.seed}}" placeholder="gilded-court-404">
|
|
</label>
|
|
</div>
|
|
|
|
<div class="delve-toggles">
|
|
<label class="checkbox"><input type="checkbox" name="maps" {{#if v.maps}}checked{{/if}}> Build the maps <span class="sub">(slower — about a second per area)</span></label>
|
|
<label class="checkbox"><input type="checkbox" name="populate" {{#if v.populate}}checked{{/if}}> Roll the encounters</label>
|
|
</div>
|
|
|
|
<footer class="delve-actions">
|
|
<button type="submit" class="bright"><i class="fas fa-mountain"></i> Raise the dungeon</button>
|
|
</footer>
|
|
</div>
|