class SeaBattle::Board

It’s Board of game Sea Battle

Attributes

board[R]
horizontal[R]
status[R]
vertical[R]

Public Class Methods

new(board = "1" * 100, status = :initialized) click to toggle source
# File lib/sea_battle/board.rb, line 14
def initialize(board = "1" * 100, status = :initialized)
  @horizontal, @vertical = 10, 10

  load_board(board)

  @status = status
  check_board
end

Public Instance Methods

activate_board() click to toggle source

When all ships are on board then board can be activated Return true when board was activated

# File lib/sea_battle/board.rb, line 25
def activate_board
  result = 0
  @board.flatten.each do |cell|
    result += 1 if cell.is_in_ship?
  end
  return false unless result == 20
  @status = :activated
  true
end
attack(row, column) click to toggle source
# File lib/sea_battle/board.rb, line 35
def attack(row, column)
  if @status == :activated
    board[row][column].attack
    is_sunken_ship?(row, column)
    is_finished?
  end
end
is_attacked?(row, column) click to toggle source
# File lib/sea_battle/board.rb, line 43
def is_attacked?(row, column)
  board[row][column].is_attacked?
end
is_in_ship?(row, column) click to toggle source
# File lib/sea_battle/board.rb, line 47
def is_in_ship?(row, column)
  board[row][column].is_in_ship?
end
is_sunken_ship?(row, column) click to toggle source

Return true if on position (row, column) is the ship which is sunked Return false if on position (row, column) is not the ship which is sunked or don’t exist the ship

# File lib/sea_battle/board.rb, line 54
def is_sunken_ship?(row, column)
  positions = ship_positions(row, column)
  return false if positions.empty?
  is_sunk = true
  positions.each do |position_row, position_column|
    is_sunk = false unless board[position_row][position_column].is_attacked?
  end
  if is_sunk
    positions.each do |position_row, position_column|
      board[position_row][position_column].sunk
    end
  end
  is_sunk
end
random_position() click to toggle source

Return position to attack (have not attacked)

# File lib/sea_battle/board.rb, line 70
def random_position
  mixed_board_positions.each do |row, column|
    return [row, column] unless is_attacked?(row, column)
  end
end
random_ships() click to toggle source

Set ships on the board (random positions)

# File lib/sea_battle/board.rb, line 77
def random_ships
  return unless @status == :initialized
  reset_board
  [1, 1, 1, 1, 2, 2, 2, 3, 3, 4].each do |length|
    RandomShip.new(self, length).add_ship
  end
end
ship_positions(row, column) click to toggle source

Return array of position ship if it will be on position [row, column]

# File lib/sea_battle/board.rb, line 86
def ship_positions(row, column)
  horizontal = horizontal_ship_position(row, column)
  vertical = vertical_ship_position(row, column)
  return horizontal if horizontal.size > vertical.size
  vertical
end

Private Instance Methods

check_board() click to toggle source

It should raise error when @board isn’t Array

# File lib/sea_battle/board.rb, line 96
def check_board
  raise "The board is not Array class" unless @board.size == 10
end
horizontal_ship_position(row, column) click to toggle source

it should return array of ship position for horizontal line with position [row, column]

# File lib/sea_battle/board.rb, line 113
def horizontal_ship_position(row, column)
  result = []
  10.times do |position|
    if @board[position][column].is_in_ship?
      result << [position, column]
    else
      break if result.include?([row, column])
      result = []
    end
  end
  result
end
is_finished?() click to toggle source
# File lib/sea_battle/board.rb, line 100
def is_finished?
  is_finished = true
  board.each do |line|
    line.each do |cell|
      is_finished = false if cell.is_in_ship? and not cell.is_sunk?
    end
  end
  @status = :finished if is_finished
  is_finished
end
load_board(board) click to toggle source
# File lib/sea_battle/board.rb, line 126
def load_board(board)
  @board = board.split("").map do |status|
    Cell.new(status.to_i)
  end.each_slice(10).to_a
end
reset_board() click to toggle source
# File lib/sea_battle/board.rb, line 132
def reset_board
  board.each do |line|
    line.each do |cell|
      cell.reset_cell
    end
  end
end
vertical_ship_position(row, column) click to toggle source

it should return array of ship position for vertical line with position [row, column]

# File lib/sea_battle/board.rb, line 142
def vertical_ship_position(row, column)
  result = []
  10.times do |position|
    if @board[row][position].is_in_ship?
      result << [row, position]
    else
      break if result.include?([row, column])
      result = []
    end
  end
  result
end