Skip to content

Map Tiles, Fog of War, and Cartography

Purpose

This file defines the actual map exploration model for the MMO.

Survey expeditions should not only return vague text or route flags. They should produce structured tile knowledge, fog-of-war clearing, and tradable cartography data.

Core Rule

The game world should be explored as tile knowledge, not as a fully revealed static map.

Players can:

  • reveal tiles for themselves
  • record tiles into chart data
  • verify old tiles again when they become stale
  • share or sell charted tile information if they have enough Cartography skill

That keeps exploration valuable over time and gives Survey expeditions a concrete output.

Map Hierarchy

Use three map layers:

1. Region Map

This is the planning layer.

  • shows major regions, towns, roads, coastlines, and known landmarks
  • used for route planning and board browsing
  • does not need fine-grained local detail

2. Area Tile Grid

This is the main exploration layer.

  • the world map is a hex grid — flat-top hexagons, axial coordinates (q, r)
  • every hex has a terrain type, movement class, and hidden content layer
  • marches travel hex by hex along a chosen path
  • fog of war is applied at this layer
  • passing through a hex and spending time exploring it produce different levels of knowledge

3. Site Footprint

This is the point-of-interest layer.

  • ruins, dens, springs, ore seams, and camps occupy one or more hexes
  • site footprints can be hidden, partial, discovered, or stale
  • a site footprint is only revealed when the hex reaches explored state — not from mere traversal

The authoritative backend stores hex ids and site ids. The client renders them as SVG hex overlays with knowledge-state styling.

Hex Movement Model

March parties move hex by hex along a chosen path. The player or the expedition resolver selects a route as a sequence of hexes.

Each hex has a movement_classroad, trail, or wilderness — that overrides the base speed for that hex. Road and trail movement classes represent maintained paths cleared through the terrain; they apply their own speed rather than the underlying terrain's wilderness modifier.

Every hex a march crosses is marked traversed at minimum. If the party stops and performs survey work in a hex, it advances to explored for that player.

For full traversal times by terrain type and the complete movement modifier table (including armor, encumbrance, and cartographer familiarity bonuses), see Tile Types Reference.

Tile Model

The map uses a flat-top hex grid with axial coordinates. Each hex stores:

  • hex_q — axial column coordinate
  • hex_r — axial row coordinate (s = -q - r is derived)
  • terrain_family — plains, forest, marsh, hills, mountain, ocean, lake, river
  • water_coverage — 0.0 to 1.0; fraction of the hex covered by a water body. Ocean and lake-deep tiles are 1.0. A river crossing a plains hex might be 0.25–0.45. Fully dry land tiles are 0.0.
  • movement_class — road, trail, wilderness (sets base speed modifier)
  • elevation_band
  • hazard_tags
  • visibility_tags
  • site_ref if present

The following fields are hidden from the player until a hex is explored (not just traversed):

  • resource_nodes — specific resources present and yield bands
  • creature_presence — creature types, density, and aggression level
  • treasure_flags — buried caches, hidden caches, ruins loot
  • site_ref (if the site footprint is concealed)
  • drift_score — staleness rate for this hex type

The game does not show hidden fields to the player until the hex is in explored or charted state.

Fog Of War States

Each player or guild tracks tile knowledge per hex in the following bands.

unknown

  • hex is hidden by full fog
  • no terrain, no route detail, no site information

rumored

  • player has heard of this area from NPCs, other players, or low-quality intel
  • vague biome type may be shown; no reliable content data
  • does not count as survey completion

traversed

  • a march party passed through this hex without stopping to explore
  • player knows: terrain type, movement cost, rough hazard level
  • player does not know: resource nodes, creature types, treasure locations, hidden sites
  • this is the minimum knowledge gained from any march that crosses a hex

explored

  • a party spent meaningful time in this hex (survey activity, deliberate exploration)
  • player knows: all traversed data plus resource nodes and yield, creature types and density, treasure possibility flags, any concealed site presence
  • this is the knowledge tier required for cartography recording and trade

charted

  • hex has been recorded into a tradable map item or archive entry
  • detail level requires explored state as source
  • includes freshness timestamp and confidence value
  • can be shared, sold, or used to fulfill survey contracts

stale

  • previously charted hex whose data has aged past its drift threshold
  • terrain and movement data remain valid; resource, creature, and event data may be outdated
  • rendered with desaturated art and a dashed warning border
  • re-exploration refreshes to explored and re-charting resets the drift clock

Survey Expedition Outputs

Survey expeditions should reveal structured tile results instead of only generic knowledge gains.

Typical outputs:

  • route strips of revealed tiles
  • local clusters around discovered sites
  • hazard notes for specific tiles
  • site footprints
  • freshness and confidence changes on already known tiles

Different survey jobs should reveal different shapes of knowledge:

Route Survey

  • reveals a corridor of tiles between two known points
  • improves route confidence and travel safety

Area Sweep

  • reveals a tile cluster around a target area
  • good for hidden sites, monster dens, and gather spots

Site Verification

  • refreshes a previously charted site and nearby tiles
  • mainly used to fight staleness

Emergency Recon

  • reveals only urgent risk tiles such as washed roads, bandit routes, plague zones, or monster pressure pockets
  • lower detail, higher urgency

Skill Split

Exploration should use two distinct but related skills:

Surveying

Surveying is about finding, confirming, and traversing.

It improves:

  • tile reveal amount
  • route confirmation
  • hidden site discovery
  • confidence on field findings

Cartography

Cartography is about recording, packaging, and sharing knowledge.

It improves:

  • how many revealed tiles can be saved into map items
  • map precision and freshness retention
  • hazard notes and annotations
  • copy quality when maps are traded or archived

Cartography Threshold Rule

The player should not automatically be able to monetize every discovered tile.

Recommended progression:

  • Untrained or Familiar: can personally reveal tiles but cannot create high-quality chart items
  • Practiced: can save specific tiles and short route strips into shareable chart data
  • Skilled: can package contiguous tile clusters and annotate hazards or site notes
  • Expert: can produce cleaner copies, merge reports, and reduce staleness loss on shared maps
  • Master: can create highly trusted archive-grade maps with strong precision and long freshness

This is the main reason Cartography should exist as its own skill.

Knowledge Quality Model

Every charted tile, route, or site record should carry three distinct values:

  • confidence: how likely the information is correct
  • freshness: how recently it was verified
  • precision: how exact the tile bounds, route corridor, or site approach is

Recommended responsibility split:

  • Surveying mostly improves discovery confidence and hidden-site confirmation
  • Cartography mostly improves recorded precision, annotation depth, and freshness retention
  • fast-changing areas such as coasts, monster dens, depleted resource sites, and event zones should lose freshness faster than stable roads or civic tiles

Suggested formulas:

confidence = field_result_quality + surveying_bonus + verification_bonus - hazard_penalty freshness_loss = base_drift × area_change_rate × event_multiplier × copy_penalty

Map Item Types

Use structured cartography goods instead of generic text notes.

tile_snapshot

  • one tile or a very small cluster
  • useful for hazard reports, rare nodes, or contract proof

route_chart

  • ordered tile corridor between two points
  • useful for travel safety and caravan work

map_sheet

  • contiguous block of charted tiles
  • useful for exploration trade and guild archives

site_chart

  • site footprint plus surrounding approach tiles
  • useful for ruins, dens, springs, seams, and seasonal sites

Each cartography item should store:

  • tile bounds
  • detail level
  • confidence rating
  • freshness value
  • annotations
  • creator identity
  • secrecy or sharing permissions

Reading or trading a chart should use those values rather than a flat rarity tag. A beautifully recorded but stale map should behave differently from a rough but freshly verified field sketch.

Copy and Lineage Rules

A chart item should remember whether it is an original field record or a copy.

  • source surveys create generation 0 originals
  • every copy increments copy_generation
  • copies can never exceed the source item's confidence, freshness, or precision
  • copied annotations should degrade before core tile bounds do

Recommended copy loss by Cartography band:

Crafter Band Confidence Loss Freshness Loss Annotation Loss
Practiced 15 15 loses one detailed annotation layer
Skilled 10 10 keeps hazards, drops fine notes first
Expert 5 5 nearly complete copy
Master 2 2 archive-grade copy

After generation 3, most map goods should be poor trade stock unless reverified in the field.

Sharing And Trade

Cartography data should move through multiple channels:

  • direct trade
  • guild archives
  • expedition group auto-share
  • contract attachments
  • market sale of map goods where allowed

Important rule:

  • personal revealed knowledge is not automatically public
  • only charted knowledge can become a tradable or shareable object

That keeps exploration and cartography distinct and valuable.

Access and Sharing Permissions

Map items and archives should support explicit permission scopes:

  • private
  • party
  • guild
  • contract-limited
  • public sale

Rules:

  • personal revealed knowledge stays private until charted into an item or archive record
  • expedition auto-share should create permissioned chart records, not leak permanent global knowledge
  • guild archives store shared copies or deposited originals, depending on guild policy
  • contract-limited maps should expire or revoke access when the contract closes if the design wants secrecy to matter

Guild Archive Rules

Guild archives should keep both provenance and a usable merged read model.

  • every submission should record contributor, submission time, and source generation
  • the archive should keep the immutable submitted version plus the current best merged version
  • archive permissions should be separable from guild treasury or officer permissions
  • archives never refresh automatically; only new survey or verification work updates them

Knowledge Import and Merge Rules

Acquiring a map item should update player knowledge without pretending the player personally visited the area.

  • high-confidence, fresh charts grant charted knowledge
  • middling charts grant rumored knowledge with usable route hints
  • stale charts import as stale
  • bought or copied charts never count as revealed; only personal travel or survey does

When multiple charts disagree, merge in this order:

  1. highest freshness
  2. highest confidence
  3. highest precision
  4. newest archive entry as tiebreaker

If two nearby sources conflict within close quality bands, mark the affected tiles or site as disputed and queue them as strong candidates for Site Verification or Route Survey.

Drift And Reverification

Map knowledge should not stay perfect forever.

Tiles can become stale because of:

  • raids
  • storms
  • monster migration
  • depleted resource sites
  • new public works or destroyed roads
  • magical or corruption events

Reverification should be a normal reason to run Survey expeditions.

Use tiered drift rates so staleness feels believable.

  • stable road and civic tiles: slow drift
  • frontier travel corridors and common resource sites: medium drift
  • coasts, monster territory, raid-prone roads, and event zones: fast drift
  • active crisis or magical anomaly zones: extreme drift until reverified

Any world event that changes roads, resource supply, monster pressure, or town building state should be allowed to write direct freshness loss to nearby tiles.

Client Model

The client renders map state as tile knowledge, not as one giant painted image. SvelteKit SVG component reads from the player's tile knowledge store and renders only what is known.

Rendering Architecture

The full 160×120 hex grid (19,200 tiles) must not be fully mounted in the SVG DOM. SVG element budget is roughly 3,000 before browser performance degrades. Use 2D viewport culling:

all tile records (plain JS flat array, precomputed px coords)
    ↓  filter by: pan offset + viewport rect + 2-hex buffer
visible tile set ($derived, ~300–500 tiles at 1080p)
    ↓  Svelte {#each} keyed by tile id
SVG DOM (only visible tiles mounted)

Pan model: translate the inner <g> group with CSS transform: translate(x, y). No individual tile coordinate changes on pan — only the group transform updates.

Buffer zone: always keep 2 hex rows/cols beyond each viewport edge in the visible set. Prevents pop-in during normal pan speed.

Filter cost: flat array scan with 4 numeric bounds checks per tile. At 19,200 tiles this runs in ~0.1ms — safe on every pointermove.

SVG Layer Stack (back to front)

Layer <g> id Content Culled?
#terrain hex fill, biome color, terrain props yes
#stale-overlay hatched overlay on stale and uncertain tiles yes
#fog fog fill, opacity by knowledge state yes
#sites site footprint icons yes
#routes road and path lines yes (by bounding box)
#annotations player markers, guild pins, event warnings no (usually sparse)
#ui tooltip targets, selection ring no

Fog Rendering

Fog is not a separate image — it is per-tile fills on the #fog layer using the same culled visible tile set.

Tile knowledge state Fog fill Opacity
unknown --bg-base solid fill 100%
traversed --bg-base solid fill 40%
surveyed none 0%
explored none 0%
stale none (stale overlay handles it separately) 0%

Map Area Completion Meter

Each named map area tracks a chart completion percentage: the fraction of its hexes the player has in surveyed, explored, or charted knowledge state (not traversed or lower).

  • Displayed as a compact percentage in the corner of the map view when that area is in focus: "Ashfen: 34% charted"
  • Shown on expedition planning screen for any expedition targeting that area
  • Updates after each expedition settlement that writes tile knowledge to the area
  • 100% completion for an area unlocks a Survey Master recognition entry in the character codex for that area — no mechanical gate, but visible in the character record and on the area map header

Completion counts only tiles the player has personally charted. Knowledge imported from a purchased chart item counts toward the map display but not toward the player's personal completion percentage.

Chunk Loading

Server tile data is loaded in area chunks, not individual tiles. Chunk boundary size should match a logical sub-region (e.g. 20×20 hex blocks). Load a chunk when pan brings its nearest edge within 3 hex rows of the current viewport edge. Client caches loaded chunks for the session; never re-request an already-loaded chunk unless explicitly marked stale by a server event.

Server-Gating Rule

The server must never send terrain content for tiles the player does not have knowledge of. Client fog is purely presentational — it is not a security boundary.

The API response for a tile chunk must be filtered server-side by the requesting player's character_tile_knowledge records before being serialised:

Knowledge state What the server sends
unknown Hex coordinates and state: unknown only. No terrain type, no biome, no content.
rumored Coordinates, state, and vague biome hint only. No terrain props, no site data.
traversed Terrain type and movement class. No hidden content layer.
surveyed Full terrain data. Hidden content layer omitted until explored.
explored Full terrain data including revealed site footprints.
charted Same as explored plus confidence and freshness metadata for cartography use.
stale Last-known data with a stale_since timestamp. Marked as potentially inaccurate.

A player who inspects their network traffic or modifies client JS must see only the above — no extra fields hidden behind the fog layer. Any terrain or content not in the player's knowledge state is absent from the payload entirely, not merely hidden client-side.

For area maps using the Tiny Swords pack, use the 64×64 terrain grid. Keep fog as its own layer above terrain but below markers and annotations.

The world map route should show:

  • known region boundaries
  • charted routes
  • fogged unexplored area tiles
  • player and guild map markers
  • event warnings on relevant tile clusters

Browser-Fit Rule

Tile discovery should be expedition-driven, not manual one-tile clicking.

The player should review map state from:

  • survey result summaries
  • route overlays
  • chart items
  • town board map requests

That keeps exploration compatible with short sessions and async resolution.

Technical Model

Core Records

Store:

  • map_area
  • map_tile
  • character_tile_knowledge
  • tile_snapshot
  • map_sheet
  • map_sheet_tile
  • map_annotation
  • guild_map_archive_entry
  • tile_drift_state
  • map_item_copy_lineage
  • map_access_grant
  • tile_knowledge_merge_log

Commands

Support commands such as:

  • start survey expedition
  • record tile knowledge from survey result
  • create tile snapshot
  • assemble map sheet
  • consume chart item
  • copy chart item
  • archive chart
  • share chart to group or guild
  • merge archive entry
  • verify stale map data

Resolution Rules

  • survey results write revealed tile knowledge first
  • cartography conversion writes charted items second
  • stale drift runs independently over time based on tile state and world events
  • map item trade references structured tile ids, not freeform text
  • using a chart item writes imported knowledge state based on freshness and confidence thresholds
  • copying or archiving a chart writes lineage and permission records
  • verification can promote rumored or stale data back toward revealed or charted
  • event or drift updates should invalidate route-safety summaries and archive freshness automatically
  • exploration, cartography, and resource discovery
  • expedition types
  • market contracts and logistics
  • dynamic events and world state
  • client and SVG pipeline