class Board
Attributes
flags_remaining[RW]
grid[R]
size[R]
Public Class Methods
new(size = 10)
click to toggle source
# File lib/minesweeper.rb, line 7 def initialize(size = 10) raise "size out of range!" unless size.between?(8, 25) @size = size @grid = Array.new(size){ Array.new(size){ Space.new } } place_mines count_nearby_mines #must be after mine placement @flags_remaining = mine_count end
Public Instance Methods
[](index)
click to toggle source
rather than just calling board.grid[col] this passes the grid directly through so you can call board[col]
# File lib/minesweeper.rb, line 54 def [](index) self.grid[index] end
endgame_render()
click to toggle source
show everything if you lose
# File lib/minesweeper.rb, line 45 def endgame_render self.grid.flatten.each {|space| space.visible = true } render end
game_lost?()
click to toggle source
# File lib/minesweeper.rb, line 93 def game_lost? touched_a_mine? end
mark_clear( x, y )
click to toggle source
# File lib/minesweeper.rb, line 69 def mark_clear( x, y ) return false if self[x][y].visible self[x][y].visible = true if self[x][y].zero_nearby? #mark all of them as well adjacent_spaces(x, y).each do |coords| adj_x, adj_y = coords[0], coords[1] mark_clear(adj_x, adj_y) end end true end
mine_count()
click to toggle source
this took lots of refactoring!!!
# File lib/minesweeper.rb, line 20 def mine_count grid.flatten.count { |space| space.mine } end
num_adjacent_mines(x, y)
click to toggle source
# File lib/minesweeper.rb, line 97 def num_adjacent_mines(x, y) mine_count = 0 adjacent_spaces(x, y).each do |coords| adj_x, adj_y = coords[0], coords[1] mine_count += 1 if self.grid[adj_x][adj_y].mine end mine_count end
place_flag( x, y )
click to toggle source
# File lib/minesweeper.rb, line 60 def place_flag( x, y ) return false if flags_remaining <= 0 return false if self[x][y].visible self[x][y].flagged = true self.flags_remaining -= 1 true end
render()
click to toggle source
# File lib/minesweeper.rb, line 24 def render (self.size-1).downto(0) do |y| print "#{y}|" (0).upto(self.size-1) do |x| render_cell(x, y) print " " end puts "|\n" end print " " print "--" * size puts "\n" print " " 0.upto(self.size-1) {|x| print " #{x}"} puts "\n" puts "Flags remaining: #{flags_remaining}\n" nil end
victory?()
click to toggle source
all non-mine spaces are visible
# File lib/minesweeper.rb, line 87 def victory? self.grid.flatten.select {|space| !space.mine }. all? {|space| space.visible } end
Private Instance Methods
adjacent_spaces(x,y)
click to toggle source
# File lib/minesweeper.rb, line 149 def adjacent_spaces(x,y) coords = [] (x - 1).upto(x + 1) do |adj_x| (y - 1).upto(y + 1) do |adj_y| # don't count yourself next if ((x == adj_x) && (y == adj_y)) #if coords are within the bounds of the grid if (adj_x >= 0 && adj_y >= 0) && (adj_x < self.size && adj_y < self.size) #add them to the list of adjacent coordinates coords.push([adj_x, adj_y]) end end end coords end
can_clear?( x, y )
click to toggle source
used to decide whether recursive clearing is possible on a space (No mine, not visible yet) AND has 0 nearby mines
# File lib/minesweeper.rb, line 135 def can_clear? ( x, y ) !self[x][y].visible && !self[x][y].mine && self[x][y].nearby_mines == 0 end
count_nearby_mines()
click to toggle source
# File lib/minesweeper.rb, line 141 def count_nearby_mines 0.upto(self.grid.size - 1) do |x| 0.upto(self.grid.size - 1) do |y| self.grid[x][y].nearby_mines = num_adjacent_mines(x, y) end end end
place_mines()
click to toggle source
# File lib/minesweeper.rb, line 172 def place_mines mines_to_place = [ (self.size - 7)**2, 100].min while mines_to_place > 0 x, y = rand(self.size), rand(self.size) unless self.grid[x][y].mine self.grid[x][y].mine = true mines_to_place -= 1 end end end
render_cell(x, y)
click to toggle source
# File lib/minesweeper.rb, line 111 def render_cell(x, y) cell = self.grid[x][y] if !cell.visible && cell.flagged print "F" elsif !cell.visible print "_" elsif cell.mine print "M" else print cell.nearby_mines end end
touched_a_mine?()
click to toggle source
oops. you found a mine
# File lib/minesweeper.rb, line 127 def touched_a_mine? self.grid.flatten.any?{ |cell| cell.visible && cell.mine } end