You can not select more than 25 topics
Topics must start with a letter or number, can include dashes ('-') and can be up to 35 characters long.
106 lines
3.7 KiB
106 lines
3.7 KiB
/** Data associated with a single cell of the map. */
|
|
import {StorageCoordinates} from "./Coordinates";
|
|
|
|
export interface HexCell {
|
|
/** A color in #RRGGBBAA format, or null indicating that the cell should simply be hidden altogether. */
|
|
readonly color: string
|
|
}
|
|
|
|
export const EMPTY_CELL: HexCell = {
|
|
color: "#FFFFFFFF"
|
|
}
|
|
|
|
export type HexLine = readonly (HexCell|null)[]
|
|
|
|
export enum HexagonOrientation {
|
|
/**
|
|
* The pointy side is vertical and the flat side is horizontal.
|
|
* Use the Y axis for pointy coordinates and the X axis for flat coordinates.
|
|
* Lines are rows that go straight across the X axis.
|
|
*/
|
|
POINTY_TOP = "POINTY_TOP",
|
|
/**
|
|
* The pointy side is horizontal and the flat side is vertical.
|
|
* Use the Y axis for flat coordinates and the X axis for pointy coordinates.
|
|
* Lines are columns that go straight down the Y axis.
|
|
*/
|
|
FLAT_TOP = "FLAT_TOP",
|
|
}
|
|
|
|
/** Which lines should be indented - odds or evens. */
|
|
export enum LineParity {
|
|
/** Odd lines (1, 3, 5, ...) are staggered inward (right or down) by 1/2 cell. */
|
|
ODD = "ODD",
|
|
/** Even lines (0, 2, 4, ...) are staggered inward (right or down) by 1/2 cell. */
|
|
EVEN = "EVEN"
|
|
}
|
|
|
|
/** The type of map this map is. */
|
|
export interface HexMapRepresentation {
|
|
readonly orientation: HexagonOrientation
|
|
readonly indentedLines: LineParity
|
|
}
|
|
|
|
/** Data corresponding to an entire hex map. */
|
|
export interface HexMap {
|
|
/** The way the map is displayed, which also affects how coordinates are calculated. */
|
|
readonly displayMode: HexMapRepresentation
|
|
/**
|
|
* The number of lines on the map.
|
|
* In ROWS and EVEN_ROWS mode, this is the height of the map.
|
|
* In COLUMNS and EVEN_COLUMNS mode, this is the width of the map.
|
|
*/
|
|
readonly lines: number
|
|
/**
|
|
* The number of cells per line.
|
|
* In ROWS and EVEN_ROWS mode, this is the width of the map.
|
|
* In COLUMNS and EVEN_COLUMNS mode, this is the height of the map.
|
|
*/
|
|
readonly cellsPerLine: number
|
|
/**
|
|
* The list of tile lines. There are always exactly {lines} lines.
|
|
* Lines have a constant length; there are always exactly {cells_per_line} cells in a line.
|
|
* In COLUMNS and EVEN_COLUMNS mode, lines represent columns.
|
|
* In ROWS and EVEN_ROWS mode, lines represent rows.
|
|
*/
|
|
readonly lineCells: readonly HexLine[]
|
|
/**
|
|
* A unique identifier in https://github.com/rs/xid format for this map. Lets the client know when it is connecting
|
|
* to a different map with the same name as this one, and its old map has been destroyed.
|
|
*/
|
|
readonly xid: string
|
|
}
|
|
|
|
export function initializeMap({lines, cellsPerLine, displayMode, xid}: {lines: number, cellsPerLine: number, displayMode: HexMapRepresentation, xid: string}): HexMap {
|
|
const lineCells: HexLine[] = [];
|
|
const emptyLine: HexCell[] = [];
|
|
for (let cell = 0; cell < cellsPerLine; cell += 1) {
|
|
emptyLine.push(EMPTY_CELL)
|
|
}
|
|
for (let line = 0; line < lines; line += 1) {
|
|
lineCells.push(emptyLine)
|
|
}
|
|
return {
|
|
lines,
|
|
cellsPerLine: cellsPerLine,
|
|
displayMode,
|
|
lineCells,
|
|
xid
|
|
}
|
|
}
|
|
|
|
export function isValidCoordinate(map: HexMap, {line, cell}: StorageCoordinates) {
|
|
return line >= 0 && line < map.lines && Number.isInteger(line)
|
|
&& cell >= 0 && cell < map.cellsPerLine && Number.isInteger(cell);
|
|
}
|
|
|
|
export function areCellsEquivalent(left: HexCell|null, right: HexCell|null): boolean {
|
|
return left === right || (left?.color === right?.color)
|
|
}
|
|
|
|
export function getCell(map: HexMap, {line, cell}: StorageCoordinates): HexCell|null {
|
|
if (!isValidCoordinate(map, {line, cell})) {
|
|
return null
|
|
}
|
|
return map.lineCells[line][cell]
|
|
} |