Documentation
¶
Overview ¶
Package grid provides generic 2D grid data structures with support for rectangular and hexagonal layouts, spatial queries, and pathfinding algorithms (BFS, UCS/Dijkstra, Greedy Best-First, A*).
Index ¶
- Variables
- func DistanceTo(from, to ints.Point, system System) int
- func HexFlatTopCellSize(width float64) floats.Size
- func HexFlatTopIsometricPixelPerfectCellSize(width float64) floats.Size
- func HexPointyTopCellSize(width float64) floats.Size
- func HexPointyTopIsometricPixelPerfectCellSize(width float64) floats.Size
- func IsometricPixelPerfectRectCellSize(width float64) floats.Size
- func IsometricRectCellSize(width float64) floats.Size
- func NeighborOffset(system System, direction Direction) ints.Vector
- func NeighborOffsets(system System) []ints.Vector
- func RectCellSize(width float64) floats.Size
- type Array
- func (a Array[T]) Clear()
- func (a Array[T]) Clone() Array[T]
- func (a Array[T]) Fill(value T)
- func (a Array[T]) Get(index ints.Point) *T
- func (a Array[T]) Has(index ints.Point) bool
- func (a Array[T]) Height() int
- func (a Array[T]) Iter() iter.Seq[ints.Point]
- func (a Array[T]) Iter2() iter.Seq2[ints.Point, *T]
- func (a Array[T]) Len() int
- func (a Array[T]) Set(index ints.Point, value T)
- func (a Array[T]) Size() ints.Size
- func (a Array[T]) Width() int
- type Cell
- func (c Cell[T]) Bounds() floats.Rectangle
- func (c Cell[T]) Center() floats.Point
- func (c Cell[T]) DistanceTo(to ints.Point) int
- func (c Cell[T]) Get() *T
- func (c Cell[T]) Index() ints.Point
- func (c Cell[T]) Neighbors() []ints.Point
- func (c Cell[T]) PathTo(to ints.Point, valid ValidFunc[T], cost CostFunc[T]) []*Cell[T]
- func (c Cell[T]) Polygon() floats.RegularPolygon
- func (c Cell[T]) Range(n int, valid ValidFunc[T]) []ints.Point
- func (c Cell[T]) Set(value T)
- func (c Cell[T]) Size() floats.Size
- func (c Cell[T]) Valid() bool
- type CostFunc
- type Direction
- type Grid
- func NewGrid[T any](layout Layout, distance func(from, to ints.Point) int, ...) *Grid[T]
- func NewHexagonFlatTopGrid[T any](size ints.Size, hexSize floats.Size, opts ...HexGridOption) *Grid[T]
- func NewHexagonPointyTopGrid[T any](size ints.Size, hexSize floats.Size, opts ...HexGridOption) *Grid[T]
- func NewIsometricRectGrid[T any](grid ints.Size, size floats.Size, opts ...RectGridOption) *Grid[T]
- func NewRectGrid[T any](grid ints.Size, size floats.Size, opts ...RectGridOption) *Grid[T]
- func (g *Grid[T]) AStar(start, goal ints.Point, valid ValidFunc[T], cost CostFunc[T]) []ints.Point
- func (g *Grid[T]) At(point floats.Point) *Cell[T]
- func (g *Grid[T]) Bounds() floats.Rectangle
- func (g *Grid[T]) BreadthFirstSearch(start, goal ints.Point, valid ValidFunc[T]) []ints.Point
- func (g *Grid[T]) BreadthFirstSearchField(start ints.Point, valid ValidFunc[T]) map[ints.Point]ints.Point
- func (g *Grid[T]) CellBounds() floats.Size
- func (g *Grid[T]) CellHeight() float64
- func (g *Grid[T]) CellSpacing() floats.Size
- func (g *Grid[T]) CellWidth() float64
- func (g *Grid[T]) Clear()
- func (g *Grid[T]) Clone() *Grid[T]
- func (g *Grid[T]) Distance(from, to ints.Point) int
- func (g *Grid[T]) Fill(value T)
- func (g *Grid[T]) Get(index ints.Point) *Cell[T]
- func (g *Grid[T]) GreedyBestFirstSearch(start, goal ints.Point, valid ValidFunc[T]) []ints.Point
- func (g *Grid[T]) Has(index ints.Point) bool
- func (g *Grid[T]) Height() int
- func (g *Grid[T]) IndexAt(point floats.Point) ints.Point
- func (g *Grid[T]) Iter(config *IterConfig) iter.Seq[*Cell[T]]
- func (g *Grid[T]) Path(from, to ints.Point, valid ValidFunc[T], cost CostFunc[T]) []*Cell[T]
- func (g *Grid[T]) Range(index ints.Point, n int, valid ValidFunc[T]) []ints.Point
- func (g *Grid[T]) Set(index ints.Point, value T)
- func (g *Grid[T]) Size() ints.Size
- func (g *Grid[T]) UniformCostSearch(start, goal ints.Point, valid ValidFunc[T], cost CostFunc[T]) []ints.Point
- func (g *Grid[T]) UniformCostSearchField(start ints.Point, valid ValidFunc[T], cost CostFunc[T]) map[ints.Point]ints.Point
- func (g *Grid[T]) Width() int
- type HexGridOption
- type IterConfig
- type Layout
- func (l Layout) Add(change floats.Vector) Layout
- func (l Layout) AlignTopLeft() Layout
- func (l Layout) Bounds() floats.Rectangle
- func (l Layout) CellBounds() floats.Size
- func (l Layout) CellPolygon(index ints.Point) floats.RegularPolygon
- func (l Layout) CellSpacing() floats.Size
- func (l Layout) FromPoint(point floats.Point) ints.Point
- func (l Layout) MoveTo(origin floats.Point) Layout
- func (l Layout) Resize(size floats.Size) Layout
- func (l Layout) Size() ints.Size
- func (l Layout) ToPoint(index ints.Point) floats.Point
- func (l Layout) With(opts ...LayoutOption) Layout
- type LayoutOption
- type Point
- func (p Point) DistanceTo(to ints.Point, system System) int
- func (p Point) FieldOfView(candidates []ints.Point, blocking []ints.Point) []ints.Point
- func (p Point) HasLineOfSight(target ints.Point, blocking []ints.Point) bool
- func (p Point) Neighbors(system System) []ints.Point
- func (p Point) Point() ints.Point
- func (p Point) Range(n int) []ints.Point
- type RectGridOption
- type System
- type Transform
- type ValidFunc
- type ValidIndexFunc
Constants ¶
This section is empty.
Variables ¶
var ( // SquareFlat maps grid (col, row) directly to screen (x, y). Each cell is a square // with circumradius = size * sqrt2/2 (the half-diagonal of the bounding box). SquareFlat = &Transform{ sides: 4, orientation: geom.FlatTop, toPoint: floats.IdentityMatrix(), fromPoint: floats.IdentityMatrix(), bounds: floats.Vec(1.0, 1.0), spacing: floats.Vec(1.0, 1.0), polygon: floats.Vec(geom.Sqrt2/2, geom.Sqrt2/2), } // SquareIsometric maps grid (col, row) to an isometric (diamond) projection: // screen_x = (col - row) * 0.5 * size.W // screen_y = (col + row) * 0.5 * size.H // For the classic ~30° game-iso look use size.W = 2 * size.H. SquareIsometric = &Transform{ sides: 4, orientation: geom.PointyTop, toPoint: floats.Mat(0.5, -0.5, 0, 0.5, 0.5, 0), fromPoint: floats.Mat(1, 1, 0, -1, 1, 0), bounds: floats.Vec(1.0, 1.0), spacing: floats.Vec(0.5, 0.5), polygon: floats.Vec(0.5, 0.5), } // HexFlatTop maps axial hex (q, r) to pixel for flat-top hexagons. HexFlatTop = &Transform{ sides: 6, orientation: geom.FlatTop, toPoint: floats.Mat(3.0/2, 0, 0, geom.Sqrt3/2, geom.Sqrt3, 0), fromPoint: floats.Mat(2.0/3, 0, 0, -1.0/3, geom.Sqrt3/3, 0), bounds: floats.Vec(2.0, geom.Sqrt3), spacing: floats.Vec(3.0/2, geom.Sqrt3), polygon: floats.Vec(1.0, 1.0), } // HexPointyTop maps axial hex (q, r) to pixel for pointy-top hexagons. HexPointyTop = &Transform{ sides: 6, orientation: geom.PointyTop, toPoint: floats.Mat(geom.Sqrt3, geom.Sqrt3/2, 0, 0, 3.0/2, 0), fromPoint: floats.Mat(geom.Sqrt3/3, -1.0/3, 0, 0, 2.0/3, 0), bounds: floats.Vec(geom.Sqrt3, 2.0), spacing: floats.Vec(geom.Sqrt3, 3.0/2), polygon: floats.Vec(1.0, 1.0), } )
Predefined grid layout transforms.
var CardinalDirections = [4]ints.Vector{ geom.Vec(1, 0), geom.Vec(0, -1), geom.Vec(-1, 0), geom.Vec(0, 1), }
CardinalDirections lists the 4 cardinal direction vectors: E, N, W, S.
var DiagonalDirections = [4]ints.Vector{ geom.Vec(1, -1), geom.Vec(-1, -1), geom.Vec(-1, 1), geom.Vec(1, 1), }
DiagonalDirections lists the 4 diagonal direction vectors: NE, NW, SW, SE.
var Directions = [8]ints.Vector{ geom.Vec(1, 0), geom.Vec(1, -1), geom.Vec(0, -1), geom.Vec(-1, -1), geom.Vec(-1, 0), geom.Vec(-1, 1), geom.Vec(0, 1), geom.Vec(1, 1), }
Directions lists all 8 direction vectors ordered counterclockwise from E.
var HexGridOpts hexGridOptions
HexGridOpts is the namespace for hexagonal grid options.
var LayoutOpts layoutOptions
var RectGridOpts rectGridOptions
RectGridOpts is the namespace for rectangular grid options.
Functions ¶
func DistanceTo ¶
DistanceTo returns the grid distance between two points for the given System. Cardinal uses Manhattan distance; Diagonal uses Chebyshev distance.
func HexFlatTopCellSize ¶ added in v1.1.0
HexFlatTopCellSize returns the circumradius for NewHexagonFlatTopGrid where each tile is exactly width pixels wide and width·√3/2 pixels tall (2:√3 ratio).
func HexFlatTopIsometricPixelPerfectCellSize ¶ added in v1.1.0
HexFlatTopIsometricPixelPerfectCellSize returns the circumradius for NewHexagonFlatTopGrid where each tile is exactly width pixels wide and width·3/4 pixels tall (4:3 ratio), suitable for pixel-perfect isometric rendering.
func HexPointyTopCellSize ¶ added in v1.1.0
HexPointyTopCellSize returns the circumradius for NewHexagonPointyTopGrid where each tile is exactly width pixels wide and width·2/√3 pixels tall (√3:2 ratio).
func HexPointyTopIsometricPixelPerfectCellSize ¶ added in v1.1.0
HexPointyTopIsometricPixelPerfectCellSize returns the circumradius for NewHexagonPointyTopGrid where each tile is exactly width pixels wide and width pixels tall (1:1 ratio), suitable for pixel-perfect isometric rendering.
func IsometricPixelPerfectRectCellSize ¶ added in v1.1.0
IsometricPixelPerfectRectCellSize returns the cell size for NewIsometricRectGrid where each diamond tile is width pixels wide and width/2 pixels tall (2:1 ratio). The 2:1 ratio is the classic pixel-art isometric convention — tile edges land on exact pixel boundaries for crisp rendering. For a geometrically accurate 30° angle use IsometricRectCellSize.
func IsometricRectCellSize ¶ added in v1.1.0
IsometricRectCellSize returns the cell size for NewIsometricRectGrid where each diamond tile is width pixels wide at a geometrically accurate 30° isometric angle (height = width·tan30° ≈ width·0.577). For a pixel-art-friendly 2:1 ratio use IsometricPixelPerfectRectCellSize.
func NeighborOffset ¶
NeighborOffset returns the unit vector for direction in the given system. For Cardinal, only even Direction values (E, N, W, S) are valid — passing a diagonal direction returns a wrong vector or panics with index out of range.
func NeighborOffsets ¶
NeighborOffsets returns neighbor direction vectors for the given System. Cardinal returns 4 vectors (E, N, W, S); Diagonal returns all 8.
func RectCellSize ¶ added in v1.1.0
RectCellSize returns the cell size for NewRectGrid where each tile is exactly width pixels wide and width pixels tall (1:1 ratio).
Types ¶
type Array ¶
type Array[T any] struct { // contains filtered or unexported fields }
Array is a 2D array.
func (Array[T]) Get ¶
Get returns a pointer to the value at index. Panics if index is out of bounds.
type Cell ¶
type Cell[T any] struct { // contains filtered or unexported fields }
Cell is a single cell in a Grid, identified by its index. It provides access to the cell's value, spatial properties, and graph operations.
func (Cell[T]) DistanceTo ¶
DistanceTo returns the grid distance from the cell to the given index.
func (Cell[T]) PathTo ¶
PathTo returns a path from the cell to the given index using A*. valid and cost are forwarded to Grid.Path.
func (Cell[T]) Polygon ¶
func (c Cell[T]) Polygon() floats.RegularPolygon
Polygon returns the regular polygon representing the cell's shape.
type Direction ¶
type Direction int
Direction represents one of the eight neighbor directions around a square cell. Directions are ordered counterclockwise starting from East (right), matching the convention used in the hexagon package.
type Grid ¶
type Grid[T any] struct { // contains filtered or unexported fields }
Grid is a 2D grid.
func NewGrid ¶
func NewGrid[T any]( layout Layout, distance func(from, to ints.Point) int, toRange func(index ints.Point, n int, valid ValidIndexFunc) []ints.Point, neighbors func(index ints.Point) []ints.Vector, ) *Grid[T]
NewGrid creates a new grid.
func NewHexagonFlatTopGrid ¶
func NewHexagonFlatTopGrid[T any](size ints.Size, hexSize floats.Size, opts ...HexGridOption) *Grid[T]
NewHexagonFlatTopGrid creates a new hexagon grid with a flat-top layout.
hexSize is the circumradius of each hex cell — the distance from the center to any vertex, which equals the edge length for a regular hexagon. Use equal W and H for an undistorted hex; different values skew the cell independently along each axis (e.g. Sz(0.5, 1) produces a hex that is compressed horizontally). The pixel bounding box of each cell is hexSize.W*2 wide and hexSize.H*√3 tall.
Grid cell (0, 0) is placed at the top-left: even columns are unshifted and odd columns are offset half a cell downward, so no cell center has a negative y coordinate.
func NewHexagonPointyTopGrid ¶
func NewHexagonPointyTopGrid[T any](size ints.Size, hexSize floats.Size, opts ...HexGridOption) *Grid[T]
NewHexagonPointyTopGrid creates a new hexagon grid with a pointy-top layout.
hexSize is the circumradius of each hex cell — the distance from the center to any vertex, which equals the edge length for a regular hexagon. Use equal W and H for an undistorted hex; different values skew the cell independently along each axis (e.g. Sz(1, 0.5) produces a hex that is compressed vertically). The pixel bounding box of each cell is hexSize.W*√3 wide and hexSize.H*2 tall.
Grid cell (0, 0) is placed at the top-left: even rows are unshifted and odd rows are offset half a cell to the right, so no cell center has a negative x coordinate.
func NewIsometricRectGrid ¶
NewIsometricRectGrid constructs a new isometric (diamond-projection) grid with 4-directional movement. Pass RectGridOpts.DiagonalMovement() to enable 8-directional movement.
func NewRectGrid ¶
NewRectGrid constructs a new rectangular grid with 4-directional (cardinal) movement. Pass RectGridOpts.DiagonalMovement() to enable 8-directional movement.
func (*Grid[T]) BreadthFirstSearch ¶
BreadthFirstSearch returns a path from start to goal.
func (*Grid[T]) BreadthFirstSearchField ¶
func (g *Grid[T]) BreadthFirstSearchField(start ints.Point, valid ValidFunc[T]) map[ints.Point]ints.Point
BreadthFirstSearchField returns a map of points to the previous point in the path.
func (*Grid[T]) CellBounds ¶
CellBounds returns the size of a cell.
func (*Grid[T]) CellHeight ¶
CellHeight returns the height of a cell.
func (*Grid[T]) CellSpacing ¶
CellSpacing returns the spacing between cell centers.
func (*Grid[T]) GreedyBestFirstSearch ¶
GreedyBestFirstSearch returns a path from start to goal.
func (*Grid[T]) Iter ¶
func (g *Grid[T]) Iter(config *IterConfig) iter.Seq[*Cell[T]]
Iter returns an iterator over grid cells in draw order (painter's algorithm). Pass nil to iterate every cell using the full grid bounds. Pass an IterConfig to restrict iteration to a viewport subset. The iteration strategy is resolved automatically from the grid layout, so tiles are always yielded back-to-front regardless of grid type. Cells at the boundary of the bounds may lie outside the grid (cell.Valid() == false).
func (*Grid[T]) UniformCostSearch ¶
func (g *Grid[T]) UniformCostSearch(start, goal ints.Point, valid ValidFunc[T], cost CostFunc[T]) []ints.Point
UniformCostSearch returns a path from start to goal.
type HexGridOption ¶
type HexGridOption func(*hexGridOptions)
HexGridOption configures a hexagonal grid constructor.
type IterConfig ¶
IterConfig configures bounds-based grid iteration. Pass a Bounds to restrict iteration to cells near the visible rectangle; one extra row and column are included on every edge so partially visible tiles are not culled. Border cells may lie outside the grid (cell.Valid() == false).
Draw order is resolved automatically from the grid layout:
- Rectangular (SquareFlat): row-major, top-to-bottom.
- Isometric (SquareIsometric): diagonal depth order (painter's algorithm) — depths (col+row) are visited in ascending screen-Y order.
- Hex flat-top (HexFlatTop): two-pass column iteration — even columns then odd — so tiles in the same visual row are drawn back-to-front.
- Hex pointy-top (HexPointyTop): row-major; the row offset is along X only, so a single pass is sufficient for correct draw order.
type Layout ¶
type Layout struct {
// contains filtered or unexported fields
}
Layout describes the mapping between grid coordinates and pixel space. Create one via NewLayout using a predefined transform (SquareFlat, HexFlatTop, etc.).
func NewLayout ¶
func NewLayout(t *Transform, opts ...LayoutOption) Layout
NewLayout creates a Layout with the given transform and cell size, with the origin at (0, 0).
func (Layout) AlignTopLeft ¶
AlignTopLeft shifts the origin so the top-left corner of cell (0, 0) sits at the world origin.
func (Layout) Bounds ¶
Bounds returns the pixel bounding box for the whole grid of cells. Grid size must be set via WithGridSize. If an index mapper was set via WithIndexMapper it is applied via ToPoint automatically.
func (Layout) CellBounds ¶
CellBounds returns the pixel bounding box of a single cell.
func (Layout) CellPolygon ¶
func (l Layout) CellPolygon(index ints.Point) floats.RegularPolygon
CellPolygon returns the regular polygon representing the cell at the given grid coordinates.
func (Layout) CellSpacing ¶
CellSpacing returns the pixel distance between adjacent cell centers along each axis.
func (Layout) ToPoint ¶
ToPoint converts offset grid coordinates to the pixel center of the cell. If an index mapper was set via WithIndexMapper, it is applied first.
func (Layout) With ¶
func (l Layout) With(opts ...LayoutOption) Layout
With returns a copy of the layout with the given options applied.
type Point ¶
Point is a grid cell coordinate with spatial query methods (Range, FieldOfView, HasLineOfSight).
func (Point) DistanceTo ¶
DistanceTo returns the grid distance between two points for the given System. Cardinal uses Manhattan distance; Diagonal uses Chebyshev distance.
func (Point) FieldOfView ¶
FieldOfView returns the subset of candidates visible from center, given a set of blocking points. Adjacent cells (Chebyshev distance ≤ 1) are always visible.
func (Point) HasLineOfSight ¶
HasLineOfSight reports whether there is a clear line of sight from src to dst, given a set of blocking points. All intermediate cells (excluding src and dst) must not be in blocking. The destination itself may be a blocker — it is visible but does not allow sight through it.
type RectGridOption ¶
type RectGridOption func(*rectGridOptions)
RectGridOption configures a rectangular grid constructor.
type System ¶
type System int
System lists the supported neighbor connectivity modes for a square grid.
type Transform ¶
type Transform struct {
// contains filtered or unexported fields
}
Transform holds the predefined coordinate mapping data for a grid layout type. Use the package-level variables (SquareFlat, SquareIsometric, HexFlatTop, HexPointyTop) or NewTransform to construct a Layout.
func NewTransform ¶
func NewTransform(sides int, orientation geom.Orientation, toPoint, fromPoint floats.Matrix, bounds, spacing, polygon floats.Vector) *Transform
NewTransform creates a custom transform for use with NewLayout. toPoint and fromPoint must be inverses of each other. bounds, spacing, and polygon are unit-space vectors scaled by the cell size at layout creation.
type ValidIndexFunc ¶
ValidIndexFunc is a function that returns true if an index is valid.