SOURCE / PINNED RELEASE
Made of little things.
Black Site Map Editor
- Release
- 32a57733b7e9…
- Author-recorded commit
- 3f54890f542f…
- License
- LICENSE
- Author’s source reference
- nostr://npub1ye5ptcxfyyxl5vjvdjar2ua3f0hynkjzpx552mu5snj3qmx5pzjscpknpr/wss%3A%2F%2Fgit.shakespeare.diy%2F/black-site-map-editor
Archive hash verified: 7a4b1abbac7db5b0…. The source-to-build association is the author’s claim; it has not been independently rebuilt.
import { html, type TemplateResult } from 'lit';
import { MAP_COLORS } from './map-renderer';
export type TutorialStep = { id: string; title: string; body: TemplateResult };
// Markup helpers. Labels match the editor's own buttons so players can find them.
const ui = (label: string) => html`<span class="ui-chip">${label}</span>`;
const key = (...keys: string[]) => keys.map((k, i) => html`${i ? '+' : ''}<kbd>${k}</kbd>`);
const tip = (content: unknown) => html`<p class="notice">${content}</p>`;
const marker = (color: string, letter: string, label: TemplateResult) =>
html`<li>
<span class="help-marker" style="--marker:${color}">${letter}</span><span>${label}</span>
</li>`;
export const tutorialSteps: TutorialStep[] = [
{
id: 'welcome',
title: 'Welcome',
body: html` <p>
This editor builds maps for Black Site: the ground, buildings, cover, guards and
loot that players fight through.
</p>
<ul>
<li><b>Centre:</b> your map. Everything you place appears here.</li>
<li>
<b>Left:</b> the map tools, grouped into Terrain, Structures, Cover &
supplies and Mission.
</li>
<li><b>Right:</b> details for the object you selected, plus the Map Check.</li>
<li>
<b>Top bar:</b> ${ui('New')} ${ui('Maps')} ${ui('Settings')} ${ui('Undo')}
${ui('Redo')} ${ui('Save draft')} ${ui('Publish')}.
</li>
</ul>
${tip(html`On a phone, the ${ui('Map')} ${ui('Tools')} ${ui('Details')} tabs switch between these areas.`)}
<p>
Use ${ui('Next')} to walk through the basics, or jump to any step from the list.
</p>`,
},
{
id: 'navigate',
title: 'Moving around',
body: html` <ul>
<li>
${ui('−')} and ${ui('+')} zoom out and in. The mouse wheel zooms towards the
pointer.
</li>
<li>${ui('Fit')} shows the whole map again.</li>
<li>
Choose ${ui('Pan map')} and drag to slide the map. With a mouse, you can also
drag with the right or middle button using any tool.
</li>
<li>${ui('Grid')} shows or hides the tile grid.</li>
</ul>
${tip('The bottom-right corner of the map toolbar shows the tile under your pointer and the map size.')}`,
},
{
id: 'terrain',
title: 'Ground & terrain',
body: html` <p>Terrain shapes where players can walk and how the map looks.</p>
<ul>
<li>${ui('Water')} blocks movement. Use it for rivers, harbours and moats.</li>
<li>${ui('Pavement')} lays hard ground for yards and lots.</li>
<li>${ui('Road')} draws roads in the map's road colour.</li>
<li>Anything you leave unpainted is open ground in the map's terrain style.</li>
</ul>
<p>
<b>To paint:</b> pick a tool, press on the map and drag. A gold box previews the
rectangle you are drawing. Let go to place it.
</p>
${tip('Change the base terrain, ground colour and road colour in Settings.')}`,
},
{
id: 'structures',
title: 'Structures',
body: html` <ul>
<li>${ui('Wall')} draws solid walls that block movement.</li>
<li>
${ui('Building')} drags out a building with a floor, outer walls and one door.
Buildings are at least 3 × 3 tiles.
</li>
</ul>
<p>
<b>Doors and rooms:</b> first select a building with ${ui('Select / move')}. Then:
</p>
<ul>
<li>
${ui('Building door')} adds another door on that building's <b>outside edge</b>.
</li>
<li>${ui('Interior wall')} splits the inside into rooms.</li>
</ul>
${tip('If a door will not place, check that it sits on the outer wall of the selected building.')}`,
},
{
id: 'cover',
title: 'Cover & supplies',
body: html` <p>Cover blocks movement and gives players something to hide behind.</p>
<ul>
<li>
${ui('Container')}: shipping containers. Pick their colour with
<b>Container color</b> in the tool panel before drawing.
</li>
<li>${ui('Tank (3×3)')}: a round storage tank. Click once to place it.</li>
<li>
${ui('Pipe')} ${ui('Crate')} ${ui('Wreck')} ${ui('Sandbag')}: smaller cover.
Drag to fill an area.
</li>
</ul>`,
},
{
id: 'mission',
title: 'Mission setup',
body: html` <p>
These markers set the map's mission: where players start, where they escape, and
what stands in the way.
</p>
<ul class="help-legend">
${marker(MAP_COLORS.insertion, 'I', html`<b>Insertion</b>: where players start. ${ui('Insertion')} moves it.`)}
${marker(MAP_COLORS.exfil, 'H', html`<b>Extraction</b>: where players escape. ${ui('Extraction')} moves it.`)}
${marker(MAP_COLORS.enemy, 'E', html`<b>Guard</b>: an enemy standing watch. Tick <b>Patrolling guards</b> first to place patrols (shown as P).`)}
${marker(MAP_COLORS.cache, 'C', html`<b>Loot cache</b>: pick <b>Cache contents</b> first: random loot, a weapon cache (shown as W) or starter supplies.`)}
</ul>
${tip('Every map has exactly one insertion and one extraction. You can move them, but not delete them.')}`,
},
{
id: 'editing',
title: 'Selecting & editing',
body: html` <ul>
<li>
Choose ${ui('Select / move')} and click an object to select it. It gets a gold
outline.
</li>
<li>
Drag a selected object to move it, or use the arrow keys (hold Shift to move 5
tiles).
</li>
<li>
The <b>Selected object</b> panel shows plain settings for it. Change them, then
press ${ui('Apply changes')}.
</li>
<li>${ui('Move selected')} shifts it by an exact number of tiles across and down.</li>
<li>
${ui('Delete')} or ${key('Delete')} removes it. ${ui('Erase object')} removes
whatever you click.
</li>
<li>
<b>Objects & layers</b> lists every object of one type, so you can find small or
hidden ones.
</li>
</ul>`,
},
{
id: 'check',
title: 'Undo & route check',
body: html` <ul>
<li>
${ui('Undo')} (${key('Ctrl', 'Z')}) and ${ui('Redo')}
(${key('Ctrl', 'Shift', 'Z')}) step back and forward through your changes.
</li>
<li>
${ui('Check route')} makes sure players can walk from insertion to extraction.
</li>
</ul>
<p>
The result appears under <b>Map check</b> on the right. If something is wrong, it
tells you what to fix, for example:
</p>
<ul>
<li>
<i>Clear a path from insertion to extraction.</i> Open a gap in walls or water.
</li>
<li>
<i>Move insertion, extraction, guards or caches onto open ground.</i> A marker
is sitting on a wall or in water.
</li>
</ul>
${tip('A map must pass the route check before it can be published.')}`,
},
{
id: 'settings',
title: 'Map settings',
body: html` <p>${ui('Settings')} holds everything about the map as a whole:</p>
<ul>
<li>
<b>Map name</b> and <b>Briefing</b>: what players see when choosing the map.
</li>
<li>
<b>Width</b> and <b>Height</b>, then ${ui('Resize grid')}. Move objects inside
the new size first.
</li>
<li><b>Terrain</b>, <b>Ground</b> and <b>Road</b> colours, and road markings.</li>
<li>
<b>Extra scenery & enemies</b>: random buildings, clutter and extra guards
and caches added each time the game starts.
</li>
<li>
<b>Map files</b>: ${ui('Download map')} saves a backup file, and you can open a
map file from your device.
</li>
</ul>`,
},
{
id: 'saving',
title: 'Saving your work',
body: html` <ul>
<li>
${ui('Save draft')} keeps your work in progress inside the host. A
<b>*</b> after the map name means there are unsaved changes.
</li>
<li>
To come back later, open ${ui('Maps')} and choose ${ui('Open saved draft')}.
</li>
<li>
Drafts are kept separately for each account, so switching accounts shows that
account's draft.
</li>
</ul>
${tip('If saving drafts is unavailable in your host, use Settings → Map files → Download map to keep a backup.')}`,
},
{
id: 'publishing',
title: 'Publishing',
body: html` <ol>
<li>Sign in through the host. The editor never sees your private keys.</li>
<li>Run ${ui('Check route')} and fix any problems.</li>
<li>
Press ${ui('Publish')}. For a map you already published, the button reads
${ui('Update map')}.
</li>
<li>Confirm. Your host may ask you to approve sharing.</li>
</ol>
<p>
Published maps are public. Other players can find them in the game and in this
editor.
</p>
${tip('Settings → Sharing & credits lets you add notes, credits and tags before you publish.')}`,
},
{
id: 'library',
title: 'Maps & remixing',
body: html` <p>${ui('Maps')} opens the maps library:</p>
<ul>
<li>
${ui('My maps')}: your published maps. ${ui('Edit')} opens one for changes;
${ui('Delete')} removes it from your published maps.
</li>
<li>${ui('Community')}: maps by other players.</li>
<li>
${ui('Built-in templates')}: the game's own maps, ready to use as a starting
point.
</li>
</ul>
<p>
<b>Remix</b> makes your own copy of any map. Remixes always credit the original
creator, and publishing one never changes their map.
</p>
${tip("You can only edit maps you published yourself. For anyone else's map, use Remix.")}`,
},
{
id: 'reference',
title: 'Quick reference',
body: html` <table class="help-table">
<tr>
<th>Action</th>
<th>Mouse & keys</th>
<th>Touch</th>
</tr>
<tr>
<td>Draw a rectangle</td>
<td>Drag with a tool</td>
<td>Drag with a tool</td>
</tr>
<tr>
<td>Pan</td>
<td>Right or middle drag, or Pan map</td>
<td>Pan map, then drag</td>
</tr>
<tr>
<td>Zoom</td>
<td>Mouse wheel, − / +</td>
<td>− / + buttons</td>
</tr>
<tr>
<td>Show whole map</td>
<td>Fit</td>
<td>Fit</td>
</tr>
<tr>
<td>Move selected</td>
<td>
Drag, or ${key('←')}${key('↑')}${key('↓')}${key('→')} (${key('Shift')} for 5
tiles)
</td>
<td>Drag, or Move selected</td>
</tr>
<tr>
<td>Delete selected</td>
<td>${key('Delete')}</td>
<td>Delete button</td>
</tr>
<tr>
<td>Undo / redo</td>
<td>${key('Ctrl', 'Z')} / ${key('Ctrl', 'Shift', 'Z')}</td>
<td>Undo / Redo</td>
</tr>
<tr>
<td>Open this help</td>
<td>${key('F1')}</td>
<td>Help</td>
</tr>
<tr>
<td>All keyboard shortcuts</td>
<td>${key('Shift', '?')}</td>
<td></td>
</tr>
</table>
${tip('Every tool also has a single-letter key. Hover a tool to see it, or press Shift + ? for the full list. Your host may change these keys.')}`,
},
];
