Skip to content

Instantly share code, notes, and snippets.

@Guevara-chan
Last active July 28, 2018 16:20
Show Gist options
  • Save Guevara-chan/88c7478b180cb0c34540ce32ae5f2add to your computer and use it in GitHub Desktop.
Save Guevara-chan/88c7478b180cb0c34540ce32ae5f2add to your computer and use it in GitHub Desktop.
Barebone minesweeper core.
# ~>Minesweeper core logic.
# ==Extnesion methods==
Function::getter = (name, proc) -> Object.defineProperty @prototype, name, {get: proc, configurable: true}
Function::setter = (name, proc) -> Object.defineProperty @prototype, name, {set: proc, configurable: true}
Boolean::either = (true_val, false_val = '') -> if @valueOf() then true_val else false_val
#.{ [Classes]
class Cell
shroud = (alert = 0b1111) << 4
bomb = flag = alert # Nibble max.
# --Methods goes here.
constructor: (@pack = 0, @shroud = @shroud) ->
@getter 'alert', () -> @pack & alert
@setter 'alert', (val) -> (@pack = (@pack & shroud) + val)
@getter 'shroud', () -> (@pack & shroud) >> 4
@setter 'shroud', (val) -> @pack = (@pack & alert) + (val << 4)
@getter 'explosive', () -> @alert is bomb
@setter 'explosive', (val) -> @alert = val.either bomb, 0
@getter 'flagged', () -> @shroud is flag
@setter 'flagged', (val) -> @shroud = val.either flag, 1
# -------------------- #
class Minefield
around = [[-1, -1], [-1, 0], [0, -1], [0, 0], [0, 1], [1, 0], [1, 1], [-1, 1], [1, -1]]
# --Methods goes here.
constructor: (@width, @height, vacancy = 0.7) ->
@sampler = new Cell 0, true
@cells = Array.from Array(@height), => new Uint8Array(@width).map =>
@sampler.explosive = Math.random() > vacancy; return @sampler.pack
@markup()
get: (x, y) ->
@cache = @sampler if 1+ @sampler.pack = @cells[y]?[x]
set: (x, y, cell = @cache) ->
return cell if 1+ @cells[y]?[x] = cell?.pack
mark: (x, y, state) ->
@set(x, y) if @get(x, y)?.flagged = state ? (not @cache.flagged)
probe: (x, y, caution = false) ->
return if (not @get x, y) or (@cache.flagged and caution)
@cache.shroud = false
return @set(x, y).explosive
detect: (x, y) ->
(@probe(x + offset[0], y + offset[1], true) for offset in around).includes true
markup: () ->
for row, y in @cells
for bits, x in row
unless (cell = new Cell bits).explosive
cell.alert++ for [tx, ty] in around when @get(x + tx, y + ty)?.explosive
@set x, y, cell
return @
#.} [Classes]
# Some mandatory export.
try [window.Cell, window.Minefield] = [Cell, Minefield]
Sign up for free to join this conversation on GitHub. Already have an account? Sign in to comment