forked from UWCS/bomberman-progcomp
-
Notifications
You must be signed in to change notification settings - Fork 0
/
ruby_example.rb
executable file
·152 lines (132 loc) · 3.64 KB
/
ruby_example.rb
1
2
3
4
5
6
7
8
9
10
11
12
13
14
15
16
17
18
19
20
21
22
23
24
25
26
27
28
29
30
31
32
33
34
35
36
37
38
39
40
41
42
43
44
45
46
47
48
49
50
51
52
53
54
55
56
57
58
59
60
61
62
63
64
65
66
67
68
69
70
71
72
73
74
75
76
77
78
79
80
81
82
83
84
85
86
87
88
89
90
91
92
93
94
95
96
97
98
99
100
101
102
103
104
105
106
107
108
109
110
111
112
113
114
115
116
117
118
119
120
121
122
123
124
125
126
127
128
129
130
131
132
133
134
135
136
137
138
139
140
141
142
143
144
145
146
147
148
149
150
151
152
#!/usr/bin/ruby
require 'socket'
class Game # class to store game information
attr_accessor :num_players, :players, :mapx, :mapy, :map, :player_x, :player_y
def initialize(my_name)
@game_over = false
@players = []
@player_x = {}
@player_y = {}
@map = Hash.new(2)
@bombs = Hash.new(-1)
# @bombs[[x, y]] is -1 if no bomb, 1..4 is the number of turns remaining on the bomb
@own_name = my_name
@map_current_row = 0
end
def new_info(incoming_message) # strings relating to game info are passed here
content = incoming_message.split ' '
if incoming_message.start_with? "MAP"
@map_y, @map_x = content[1], content[2]
elsif incoming_message.start_with? "PLAYERS"
@num_players, @players_alive = content[1], content[1]
@name_context = :players
elsif incoming_message.start_with? "DEAD" then
@name_context = :dead
elsif incoming_message.start_with? "END"
@game_over = true
elsif incoming_message.start_with? "ACTIONS" then
tick_bombs()
@name_context = :actions
elsif incoming_message =~ /^\d.*/ then
content.length.times do |i|
@map[[@map_current_row, i]] = content[i]
end
@map_current_row.succ
p @map
elsif incoming_message =~ /^[a-z].*/
self.name_info incoming_message
else
p "zed0, fix the server! (or more likely MikeCobra fix the Ruby!)"
end
end
def name_info(name_message)
content = name_message.split ' '
if @name_context == :players then
@players.push content[0]
@player_y[content[0]] = content[1].to_i
@player_x[content[0]] = content[2].to_i
elsif @name_context == :dead
@players.delete content[0]
elsif @name_context == :actions then
if content[1] == "BOMB"
self.update_bombs(content[0])
elsif ["UP", "LEFT", "DOWN", "RIGHT"].include? content[1]
self.move(content[0], content[1])
end
end
end
def tick_bombs
@bombs.each do |key, value|
@bombs[key] = -1 if value == 1
@bombs[key] = value - 1 if value != -1
end
end
def move(player, direction)
x = @player_x[player]
y = @player_y[player]
if direction == "UP" then
@player_y = (y - 1) if can_move?([x, y - 1])
elsif direction == "RIGHT"
@player_x = (x + 1) if can_move?([x + 1, y])
elsif direction == "DOWN"
@player_y = (y + 1) if can_move?([x, y + 1])
elsif direction == "LEFT"
@player_x = (x - 1) if can_move?([x - 1, y])
end
end
def can_move?(square)
((@map[square] == 0 ) & (@bombs[square] == -1))
end
def update_bombs(player)
x = @player_x[player]
y = @player_y[player]
@bombs[[x, y]] = 4 if @bombs[[x, y]] == -1
end
def my_x
@player_x[@own_name]
end
def my_y
@player_y[@own_name]
end
def over?
@game_over
end
def alive?
@players.include? @own_name
end
end
class Array
def random_element
self[rand(self.length)]
end
end
class AI # the AI class
# Insert Magical AI System Here
def response(game_state) # this is called when it's time to move, game_state contains info about the game
p game_state.over?
["BOMB", "UP", "LEFT", "DOWN", "RIGHT"].random_element if game_state.alive? # Don't even bother to check I can move there
end
end
player_name = "rubbish-ruby"
password = "reallydamnsecure"
while true do
socket = TCPSocket.new 'uwcs.co.uk', 8037
game = Game.new player_name
ai = AI.new
while !game.over? do
line = socket.gets
p line
if line.start_with? "INIT"
socket.print "REGISTER #{player_name} #{password}"
elsif line.start_with? "MAP", "ACTIONS", "PLAYERS", "DEAD", "END"
game.new_info line
elsif line =~ /^\d.*/
game.new_info line
elsif line =~ /^[a-z].*/
game.new_info line
elsif line.start_with? "TICK"
response = ai.response game
socket.print "ACTION " + response if response != nil
end
end
end