software_challenge_client 0.1.1 → 0.1.3
This diff represents the content of publicly available package versions that have been released to one of the supported registries. The information contained in this diff is provided for informational purposes only and reflects changes between package versions as they appear in their respective public registries.
- checksums.yaml +4 -4
- data/README.md +2 -1
- data/RELEASES.md +7 -0
- data/lib/software_challenge_client/board.rb +39 -39
- data/lib/software_challenge_client/client_interface.rb +1 -1
- data/lib/software_challenge_client/condition.rb +2 -2
- data/lib/software_challenge_client/connection.rb +15 -9
- data/lib/software_challenge_client/debug_hint.rb +6 -6
- data/lib/software_challenge_client/field.rb +7 -7
- data/lib/software_challenge_client/game_state.rb +33 -33
- data/lib/software_challenge_client/move.rb +6 -6
- data/lib/software_challenge_client/network.rb +15 -15
- data/lib/software_challenge_client/player.rb +3 -3
- data/lib/software_challenge_client/player_color.rb +1 -1
- data/lib/software_challenge_client/protocol.rb +8 -8
- data/lib/software_challenge_client/version.rb +1 -1
- metadata +3 -3
checksums.yaml
CHANGED
@@ -1,7 +1,7 @@
|
|
1
1
|
---
|
2
2
|
SHA1:
|
3
|
-
metadata.gz:
|
4
|
-
data.tar.gz:
|
3
|
+
metadata.gz: 31495d828f8c74923ec05f993fac6c9ede09cc24
|
4
|
+
data.tar.gz: f39a179740dcf650a29f5d935a812a514f875ec7
|
5
5
|
SHA512:
|
6
|
-
metadata.gz:
|
7
|
-
data.tar.gz:
|
6
|
+
metadata.gz: 6a20c8cf937d09ebd0a4176018e2f9d414a44e17d44c82e3fd832c5c95f5dc00cdf0592e7937775a2d25aee575bc4e86449a629075d577807c7c6383ea80a129
|
7
|
+
data.tar.gz: 04fec5b6316034416e066c75214aa5d717ee7f1f5cc93bd5cc291c159dace9f8e0b9a8162b3f9ed5fdb0a89c6656be0cfe18e38b42fb02727a20ed7584ae8c31
|
data/README.md
CHANGED
@@ -57,4 +57,5 @@ Bug reports and pull requests are welcome on GitHub at
|
|
57
57
|
https://github.com/CAU-Kiel-Tech-Inf/socha_ruby_client. This project
|
58
58
|
is intended to be a safe, welcoming space for collaboration, and
|
59
59
|
contributors are expected to adhere to the
|
60
|
-
[
|
60
|
+
[code of conduct](CODE_OF_CONDUCT.md) (from
|
61
|
+
[Contributor Covenant](http://contributor-covenant.org)).
|
data/RELEASES.md
CHANGED
@@ -16,11 +16,11 @@ class Board
|
|
16
16
|
# @!attribute [r] connections
|
17
17
|
# @return [Array<Connection>] the board's connections
|
18
18
|
attr_reader :connections
|
19
|
-
|
19
|
+
|
20
20
|
def initialize
|
21
21
|
self.init
|
22
22
|
end
|
23
|
-
|
23
|
+
|
24
24
|
# Initializes the board
|
25
25
|
#
|
26
26
|
# @param init [Boolean] if 'true', then the board will be initialized with swamps, otherwise the board will be completely empty
|
@@ -31,9 +31,9 @@ class Board
|
|
31
31
|
self.makeClearBoard
|
32
32
|
end
|
33
33
|
end
|
34
|
-
|
34
|
+
|
35
35
|
# Initializes the board with swamps
|
36
|
-
def init
|
36
|
+
def init
|
37
37
|
@fields = Array.new(Constants::SIZE) {Array.new(Constants::SIZE)}
|
38
38
|
@fields[0][0] = Field.new(FieldType::SWAMP, 0, 0)
|
39
39
|
@fields[0][Constants::SIZE - 1] = Field.new(FieldType::SWAMP, 0, Constants::SIZE - 1)
|
@@ -48,14 +48,14 @@ class Board
|
|
48
48
|
@fields[Constants::SIZE - 1][y] = Field.new(FieldType::BLUE, Constants::SIZE - 1, y);
|
49
49
|
end
|
50
50
|
for x in 1..(Constants::SIZE - 2)
|
51
|
-
for y in 1..(Constants::SIZE - 2)
|
51
|
+
for y in 1..(Constants::SIZE - 2)
|
52
52
|
@fields[x][y] = Field.new(FieldType::NORMAL, x, y);
|
53
53
|
end
|
54
54
|
end
|
55
55
|
self.placeSwamps()
|
56
56
|
@connections = Array.new;
|
57
57
|
end
|
58
|
-
|
58
|
+
|
59
59
|
# Places swamps at random coordinates
|
60
60
|
def placeSwamps
|
61
61
|
# big swamp
|
@@ -88,25 +88,25 @@ class Board
|
|
88
88
|
self.fields[x][y].type = FieldType::SWAMP
|
89
89
|
end
|
90
90
|
|
91
|
-
|
92
|
-
# creates a cleared board
|
91
|
+
|
92
|
+
# creates a cleared board
|
93
93
|
def makeClearBoard
|
94
|
-
@fields = Array.new(Constants::SIZE
|
94
|
+
@fields = Array.new(Constants::SIZE) {Array.new(Constants::SIZE)}
|
95
95
|
@connections = Array.new
|
96
96
|
end
|
97
|
-
|
97
|
+
|
98
98
|
# gets the owner's color for the field at the coordinate (x, y)
|
99
|
-
#
|
99
|
+
#
|
100
100
|
# @param x [Integer] x-coordinate
|
101
101
|
# @param y [Integer] y-coordinate
|
102
102
|
# @return [PlayerColor] owner's color of field (x, y)
|
103
|
-
def getOwnerColor(x, y)
|
103
|
+
def getOwnerColor(x, y)
|
104
104
|
return self.fields[x][y].ownerColor
|
105
105
|
end
|
106
|
-
|
107
|
-
|
106
|
+
|
107
|
+
|
108
108
|
# sets the owner's color for the field at the coordinate (x, y)
|
109
|
-
#
|
109
|
+
#
|
110
110
|
# @param x [Integer] x-coordinate
|
111
111
|
# @param y [Integer] y-coordinate
|
112
112
|
# @param player [Player] new owner of field (x, y)
|
@@ -116,7 +116,7 @@ class Board
|
|
116
116
|
end
|
117
117
|
|
118
118
|
# creates wires at the coordinate (x, y), if it is possible
|
119
|
-
#
|
119
|
+
#
|
120
120
|
# @param x [Integer] x-coordinate
|
121
121
|
# @param y [Integer] y-coordinate
|
122
122
|
def createNewWires(x, y)
|
@@ -144,11 +144,11 @@ class Board
|
|
144
144
|
if self.checkPossibleWire(x, y, x + 1, y + 2)
|
145
145
|
self.createWire(x, y, x + 1, y + 2)
|
146
146
|
end
|
147
|
-
|
148
|
-
end
|
147
|
+
|
148
|
+
end
|
149
149
|
|
150
150
|
# creates a new wire
|
151
|
-
#
|
151
|
+
#
|
152
152
|
# @param x1 [Integer] x-coordinate starting point
|
153
153
|
# @param y1 [Integer] y-coordinate starting point
|
154
154
|
# @param x2 [Integer] x-coordinate ending point
|
@@ -158,7 +158,7 @@ class Board
|
|
158
158
|
end
|
159
159
|
|
160
160
|
# checks, if a wire can be placed at specified coordinates
|
161
|
-
#
|
161
|
+
#
|
162
162
|
# @param x1 [Integer] x-coordinate starting point
|
163
163
|
# @param y1 [Integer] y-coordinate starting point
|
164
164
|
# @param x2 [Integer] x-coordinate ending point
|
@@ -174,7 +174,7 @@ class Board
|
|
174
174
|
end
|
175
175
|
|
176
176
|
# checks, if a blocking wire exists
|
177
|
-
#
|
177
|
+
#
|
178
178
|
# @param x1 [Integer] x-coordinate starting point
|
179
179
|
# @param y1 [Integer] y-coordinate starting point
|
180
180
|
# @param x2 [Integer] x-coordinate ending point
|
@@ -187,7 +187,7 @@ class Board
|
|
187
187
|
for y in smallerY..biggerY # checks all 6 Fields, from
|
188
188
|
# where there could be
|
189
189
|
# blocking connections
|
190
|
-
if !self.fields[x][y].ownerColor.nil? && (x != x1 || y != y1) &&
|
190
|
+
if !self.fields[x][y].ownerColor.nil? && (x != x1 || y != y1) &&
|
191
191
|
(x != x2 || y != y2) # excludes the Fields with no owner and
|
192
192
|
# the fields (x1, y2), (x2, y2)
|
193
193
|
# themselves.
|
@@ -199,9 +199,9 @@ class Board
|
|
199
199
|
end
|
200
200
|
return false
|
201
201
|
end
|
202
|
-
|
202
|
+
|
203
203
|
# gets connections for the coordinate (x, y)
|
204
|
-
#
|
204
|
+
#
|
205
205
|
# @param x [Integer] x-coordinate
|
206
206
|
# @param y [Integer] y-coordinate
|
207
207
|
# @return [Array] Array of connections from field (x, y)
|
@@ -209,7 +209,7 @@ class Board
|
|
209
209
|
xyConnections = Array.new
|
210
210
|
if !self.connections.nil?
|
211
211
|
for c in self.connections
|
212
|
-
if c.x1 == x && c.y1 == y
|
212
|
+
if c.x1 == x && c.y1 == y
|
213
213
|
xyConnections.push(Connection.new(x, y, c.x2, c.y2, c.ownerColor))
|
214
214
|
end
|
215
215
|
if c.x2 == x && c.y2 == y
|
@@ -229,11 +229,11 @@ class Board
|
|
229
229
|
end
|
230
230
|
return false
|
231
231
|
end
|
232
|
-
|
232
|
+
|
233
233
|
def orientation(px,py,qx,qy,rx,ry)
|
234
234
|
val = (qy - py) * (rx - qx) -
|
235
235
|
(qx - px) * (ry - qy)
|
236
|
-
|
236
|
+
|
237
237
|
if val == 0
|
238
238
|
return 0
|
239
239
|
end
|
@@ -242,44 +242,44 @@ class Board
|
|
242
242
|
end
|
243
243
|
return 2
|
244
244
|
end
|
245
|
-
|
245
|
+
|
246
246
|
def doIntersect(p1x,p1y, q1x,q1y, p2x,p2y, q2x,q2y)
|
247
247
|
o1 = orientation(p1x,p1y, q1x,q1y, p2x,p2y)
|
248
248
|
o2 = orientation(p1x,p1y, q1x,q1y, q2x,q2y)
|
249
249
|
o3 = orientation(p2x,p2y, q2x,q2y, p1x,p1y)
|
250
250
|
o4 = orientation(p2x,p2y, q2x,q2y, q1x,q1y)
|
251
|
-
|
251
|
+
|
252
252
|
if o1 != o2 && o3 != o4
|
253
253
|
return true
|
254
254
|
end
|
255
|
-
|
255
|
+
|
256
256
|
if o1 == 0 && onSegment(p1x,p1y, p2x,p2y, q1x,q1y)
|
257
257
|
return true
|
258
258
|
end
|
259
|
-
|
259
|
+
|
260
260
|
if o2 == 0 && onSegment(p1x,p1y, q2x,q2y, q1x,q1y)
|
261
261
|
return true
|
262
262
|
end
|
263
|
-
|
263
|
+
|
264
264
|
if o3 == 0 && onSegment(p2x,p2x, p1x,p1y, q2x,q2y)
|
265
265
|
return true
|
266
266
|
end
|
267
|
-
|
267
|
+
|
268
268
|
if o4 == 0 && onSegment(p2x,p2y, q1x,q1y, q2x,q2y)
|
269
269
|
return true
|
270
270
|
end
|
271
|
-
|
271
|
+
|
272
272
|
return false
|
273
273
|
end
|
274
274
|
|
275
275
|
# checks for the wire (x1, y1) -> (x2, y2), if it is blocked by any connection going out from (x,y).
|
276
|
-
#
|
276
|
+
#
|
277
277
|
# @param x1 [Integer] x-coordinate starting point
|
278
278
|
# @param y1 [Integer] y-coordinate starting point
|
279
279
|
# @param x2 [Integer] x-coordinate ending point
|
280
280
|
# @param y2 [Integer] y-coordinate ending point
|
281
281
|
# @param x [Integer] x-coordinate comparison field
|
282
|
-
# @param y [Integer] y-coordinate comparison field
|
282
|
+
# @param y [Integer] y-coordinate comparison field
|
283
283
|
# @return [Boolean] 'true', if another wire would block the creation of a new wire at specified coordinates
|
284
284
|
def isWireBlocked(x1, y1, x2, y2, x, y)
|
285
285
|
for c in getConnections(x, y)
|
@@ -293,7 +293,7 @@ class Board
|
|
293
293
|
def to_s
|
294
294
|
return self.fields.map { |f| f.map {|i| (i.ownerColor==PlayerColor::RED ? 'R' : (i.ownerColor==PlayerColor::BLUE ? 'B' : (i.type==FieldType::SWAMP ? 'S' : (i.type==FieldType::RED ? 'r' : (i.type==FieldType::BLUE ? 'b' : ' '))))) }.join(",")}.join("\n")
|
295
295
|
end
|
296
|
-
|
296
|
+
|
297
297
|
def ==(another_board)
|
298
298
|
for x in 0..(Constants.SIZE - 1)
|
299
299
|
for y in 0..(Constants.SIZE - 1)
|
@@ -310,7 +310,7 @@ class Board
|
|
310
310
|
return false
|
311
311
|
end
|
312
312
|
end
|
313
|
-
|
313
|
+
|
314
314
|
return true;
|
315
315
|
end
|
316
|
-
end
|
316
|
+
end
|
@@ -10,7 +10,7 @@ class Condition
|
|
10
10
|
# @!attribute [r] reason
|
11
11
|
# @return [String] winning reason
|
12
12
|
attr_reader :reason
|
13
|
-
|
13
|
+
|
14
14
|
# Initializes the winning Condition with a player and a reason
|
15
15
|
# @param winer [Player] winning player
|
16
16
|
# @param reason [String] winning reason
|
@@ -18,5 +18,5 @@ class Condition
|
|
18
18
|
@winner = winner
|
19
19
|
@reason = reason
|
20
20
|
end
|
21
|
-
|
21
|
+
|
22
22
|
end
|
@@ -19,32 +19,38 @@ class Connection
|
|
19
19
|
# @!attribute [r] ownerColor
|
20
20
|
# @return [PlayerColor] connection's owner's color
|
21
21
|
attr_reader :ownerColor
|
22
|
-
|
22
|
+
|
23
23
|
# Initializer
|
24
|
-
#
|
24
|
+
#
|
25
25
|
# @param x1 [Integer] x-coordinate starting point
|
26
26
|
# @param y1 [Integer] y-coordinate starting point
|
27
27
|
# @param x2 [Integer] x-coordinate ending point
|
28
28
|
# @param y2 [Integer] y-coordinate ending point
|
29
29
|
# @param owner [PlayerColor] connection's owner's color
|
30
|
-
def initialize(x1, y1, x2, y2, ownerColor)
|
30
|
+
def initialize(x1, y1, x2, y2, ownerColor)
|
31
31
|
@x1 = x1
|
32
32
|
@x2 = x2
|
33
33
|
@y1 = y1
|
34
34
|
@y2 = y2
|
35
35
|
@ownerColor = ownerColor
|
36
36
|
end
|
37
|
-
|
37
|
+
|
38
38
|
def ==(another_connection)
|
39
|
-
if(self.x1 == another_connection.x1 &&
|
40
|
-
|
41
|
-
|
39
|
+
if (self.x1 == another_connection.x1 &&
|
40
|
+
self.y1 == another_connection.y1 &&
|
41
|
+
self.x2 == another_connection.x2 &&
|
42
|
+
self.y2 == another_connection.y2 ||
|
43
|
+
self.x1 == another_connection.x2 &&
|
44
|
+
self.y1 == another_connection.y2 &&
|
45
|
+
self.x2 == another_connection.x1 &&
|
46
|
+
self.y2 == another_connection.y1)
|
47
|
+
return ownerColor == another_connection.ownerColor
|
42
48
|
else
|
43
49
|
return false
|
44
50
|
end
|
45
51
|
end
|
46
|
-
|
52
|
+
|
47
53
|
def to_s
|
48
54
|
return "#{self.ownerColor} : (#{self.x1}, #{self.y1}) - (#{self.x2}, #{self.y2})"
|
49
55
|
end
|
50
|
-
end
|
56
|
+
end
|
@@ -2,11 +2,11 @@
|
|
2
2
|
# @author Ralf-Tobias Diekert
|
3
3
|
# A debug hint, that can be added to a move
|
4
4
|
class DebugHint
|
5
|
-
|
5
|
+
|
6
6
|
# @!attribute [r] content
|
7
7
|
# @return [String] a hint
|
8
8
|
attr_reader :content
|
9
|
-
|
9
|
+
|
10
10
|
# @overload initialize
|
11
11
|
# Creates an empty hint
|
12
12
|
# @overload initialize(key, value)
|
@@ -17,17 +17,17 @@ class DebugHint
|
|
17
17
|
# Creates a hint with specified content
|
18
18
|
# @param content of the hint
|
19
19
|
def initialize
|
20
|
-
|
20
|
+
|
21
21
|
end
|
22
|
-
|
22
|
+
|
23
23
|
def initialize(key, value)
|
24
24
|
if key.nil?
|
25
25
|
self.content = "#{value}"
|
26
|
-
else
|
26
|
+
else
|
27
27
|
self.content = "#{key} = #{value}"
|
28
28
|
end
|
29
29
|
end
|
30
|
-
|
30
|
+
|
31
31
|
def initialize(content)
|
32
32
|
self.content = "#{content}"
|
33
33
|
end
|
@@ -17,9 +17,9 @@ class Field
|
|
17
17
|
# @!attribute [r] y
|
18
18
|
# @return [Integer] the field's y-coordinate
|
19
19
|
attr_reader :y
|
20
|
-
|
20
|
+
|
21
21
|
# Initializer
|
22
|
-
#
|
22
|
+
#
|
23
23
|
# @param type [FieldType] field type
|
24
24
|
# @param x [Integer] x-coordinate
|
25
25
|
# @param y [Integer] y-coordinate
|
@@ -29,14 +29,14 @@ class Field
|
|
29
29
|
@x = x
|
30
30
|
@y = y
|
31
31
|
end
|
32
|
-
|
32
|
+
|
33
33
|
def ==(another_field)
|
34
|
-
return self.ownerColor == another_field.ownerColor &&
|
35
|
-
self.type == another_field.type &&
|
36
|
-
self.x == another_field.x &&
|
34
|
+
return self.ownerColor == another_field.ownerColor &&
|
35
|
+
self.type == another_field.type &&
|
36
|
+
self.x == another_field.x &&
|
37
37
|
self.y == another_field.y
|
38
38
|
end
|
39
|
-
|
39
|
+
|
40
40
|
def to_s
|
41
41
|
return "Field: x = #{self.x}, y = #{self.y}, owner = #{self.ownerColor}, type = #{self.type}"
|
42
42
|
end
|
@@ -10,7 +10,7 @@ require_relative 'field_type'
|
|
10
10
|
# @author Ralf-Tobias Diekert
|
11
11
|
# The state of a game
|
12
12
|
class GameState
|
13
|
-
|
13
|
+
|
14
14
|
# @!attribute [rw] turn
|
15
15
|
# @return [Integer] turn number
|
16
16
|
attr_accessor :turn
|
@@ -35,18 +35,18 @@ class GameState
|
|
35
35
|
# @!attribute [rw] condition
|
36
36
|
# @return [Condition] the winner and winning reason
|
37
37
|
attr_accessor :condition
|
38
|
-
|
38
|
+
|
39
39
|
def initialize
|
40
40
|
self.currentPlayerColor = PlayerColor::RED
|
41
41
|
self.startPlayerColor = PlayerColor::RED
|
42
42
|
self.board = Board.new(true)
|
43
43
|
end
|
44
|
-
|
44
|
+
|
45
45
|
# adds a player to the gamestate
|
46
46
|
#
|
47
47
|
# @param player [Player] the player, that will be added
|
48
|
-
def addPlayer(player)
|
49
|
-
if player.color == PlayerColor::RED
|
48
|
+
def addPlayer(player)
|
49
|
+
if player.color == PlayerColor::RED
|
50
50
|
@red = player
|
51
51
|
else if player.color == PlayerColor::BLUE
|
52
52
|
@blue = player
|
@@ -66,34 +66,34 @@ class GameState
|
|
66
66
|
end
|
67
67
|
|
68
68
|
# gets the other (not the current) player
|
69
|
-
#
|
69
|
+
#
|
70
70
|
# @return [Player] the other (not the current) player
|
71
71
|
def otherPlayer
|
72
72
|
if self.currentPlayerColor == PlayerColor::RED
|
73
|
-
return self.blue
|
73
|
+
return self.blue
|
74
74
|
else
|
75
75
|
return self.red
|
76
76
|
end
|
77
77
|
end
|
78
|
-
|
78
|
+
|
79
79
|
# gets the other (not the current) player's color
|
80
80
|
#
|
81
81
|
# @return [PlayerColor] the other (not the current) player's color
|
82
82
|
def otherPlayerColor
|
83
83
|
return PlayerColor.opponentColor(self.currentPlayerColor)
|
84
84
|
end
|
85
|
-
|
85
|
+
|
86
86
|
# gets the start player
|
87
87
|
#
|
88
88
|
# @return [Player] the startPlayer
|
89
89
|
def startPlayer
|
90
|
-
if self.startPlayer == PlayerColor::RED
|
90
|
+
if self.startPlayer == PlayerColor::RED
|
91
91
|
return self.red
|
92
92
|
else
|
93
93
|
return self.blue
|
94
94
|
end
|
95
95
|
end
|
96
|
-
|
96
|
+
|
97
97
|
# switches current player
|
98
98
|
def switchCurrentPlayer
|
99
99
|
if currentPlayer.color == PlayerColor::RED
|
@@ -102,7 +102,7 @@ class GameState
|
|
102
102
|
@currentPlayer = self.red
|
103
103
|
end
|
104
104
|
end
|
105
|
-
|
105
|
+
|
106
106
|
# prepares next turn and sets the last move
|
107
107
|
#
|
108
108
|
# @param [Move] the last move
|
@@ -111,14 +111,14 @@ class GameState
|
|
111
111
|
@lastMove = lastMove;
|
112
112
|
self.switchCurrentPlayer()
|
113
113
|
end
|
114
|
-
|
114
|
+
|
115
115
|
# gets the current round
|
116
116
|
#
|
117
117
|
# @return [Integer] the current round
|
118
118
|
def round
|
119
119
|
return self.turn / 2
|
120
120
|
end
|
121
|
-
|
121
|
+
|
122
122
|
# gets all possible moves
|
123
123
|
#
|
124
124
|
# @return [Array<Move>] a list of all possible moves
|
@@ -136,18 +136,18 @@ class GameState
|
|
136
136
|
end
|
137
137
|
return moves
|
138
138
|
end
|
139
|
-
|
139
|
+
|
140
140
|
# performs a move on the gamestate
|
141
141
|
#
|
142
142
|
# @param move [Move] the move, that will be performed
|
143
143
|
# @param player [Player] the player, who makes the move
|
144
144
|
def perform(move, player)
|
145
145
|
if !move.nil?
|
146
|
-
if move.x < Constants::SIZE && move.y < Constants::SIZE &&
|
146
|
+
if move.x < Constants::SIZE && move.y < Constants::SIZE &&
|
147
147
|
move.x >= 0 && move.y >= 0
|
148
|
-
if self.getPossibleMoves.include?(move)
|
148
|
+
if self.getPossibleMoves.include?(move)
|
149
149
|
self.board.put(move.x, move.y, player)
|
150
|
-
player.points = self.pointsForPlayer(player)
|
150
|
+
player.points = self.pointsForPlayer(player)
|
151
151
|
else
|
152
152
|
raise "Der Zug ist nicht möglich, denn der Platz ist bereits besetzt oder nicht besetzbar."
|
153
153
|
end
|
@@ -156,7 +156,7 @@ class GameState
|
|
156
156
|
end
|
157
157
|
end
|
158
158
|
end
|
159
|
-
|
159
|
+
|
160
160
|
# gets a player's points
|
161
161
|
#
|
162
162
|
# @param player [Player] the player, whos statistics will be returned
|
@@ -164,19 +164,19 @@ class GameState
|
|
164
164
|
def playerStats(player)
|
165
165
|
return self.playerStats(player.color)
|
166
166
|
end
|
167
|
-
|
167
|
+
|
168
168
|
# gets a player's points by the player's color
|
169
169
|
#
|
170
170
|
# @param playerColor [PlayerColor] the player's color, whos statistics will be returned
|
171
171
|
# @return [Integer] the points of the player
|
172
|
-
def playerStats(playerColor)
|
172
|
+
def playerStats(playerColor)
|
173
173
|
if playerColor == PlayerColor::RED
|
174
174
|
return self.gameStats[0];
|
175
|
-
else
|
175
|
+
else
|
176
176
|
return self.gameStats[1]
|
177
177
|
end
|
178
178
|
end
|
179
|
-
|
179
|
+
|
180
180
|
# gets the players' statistics
|
181
181
|
#
|
182
182
|
# @return [Array<Integer>] the points for both players
|
@@ -185,17 +185,17 @@ class GameState
|
|
185
185
|
|
186
186
|
stats[0][0] = self.red.points
|
187
187
|
stats[1][0] = self.blue.points
|
188
|
-
|
188
|
+
|
189
189
|
return stats
|
190
190
|
end
|
191
|
-
|
191
|
+
|
192
192
|
# get the players' names
|
193
193
|
#
|
194
194
|
# @return [Array<String>] the names for both players
|
195
195
|
def playerNames
|
196
196
|
return [red.displayName, blue.displayName]
|
197
197
|
end
|
198
|
-
|
198
|
+
|
199
199
|
# sets the game-ended condition
|
200
200
|
#
|
201
201
|
# @param winner [Player] the winner of the game
|
@@ -205,28 +205,28 @@ class GameState
|
|
205
205
|
@condition = Condition.new(winner, reason)
|
206
206
|
end
|
207
207
|
end
|
208
|
-
|
208
|
+
|
209
209
|
# has the game ended?
|
210
210
|
#
|
211
211
|
# @return [Boolean] true, if the game has allready ended
|
212
212
|
def gameEnded?
|
213
213
|
return !self.condition.nil?
|
214
214
|
end
|
215
|
-
|
215
|
+
|
216
216
|
# gets the game's winner
|
217
217
|
#
|
218
218
|
# @return [Player] the game's winner
|
219
219
|
def winner
|
220
220
|
return condition.nil? ? nil : self.condition.winner
|
221
221
|
end
|
222
|
-
|
222
|
+
|
223
223
|
# gets the winning reason
|
224
224
|
#
|
225
225
|
# @return [String] the winning reason
|
226
226
|
def winningReason
|
227
227
|
return condition.nil? ? nil : self.condition.reason
|
228
228
|
end
|
229
|
-
|
229
|
+
|
230
230
|
# calculates a player's points
|
231
231
|
#
|
232
232
|
# @param player [Player] the player, whos point will be calculated
|
@@ -271,7 +271,7 @@ class GameState
|
|
271
271
|
longestPath = fields[1].x - fields[0].x
|
272
272
|
end
|
273
273
|
end
|
274
|
-
|
274
|
+
|
275
275
|
return longestPath # return longestPath
|
276
276
|
end
|
277
277
|
|
@@ -336,9 +336,9 @@ class GameState
|
|
336
336
|
circuit.push(*toBeAddedFields)
|
337
337
|
if changed
|
338
338
|
return self.circuit(circuit, visited)
|
339
|
-
else
|
339
|
+
else
|
340
340
|
return circuit
|
341
341
|
end
|
342
342
|
end
|
343
|
-
|
343
|
+
|
344
344
|
end
|
@@ -13,9 +13,9 @@ class Move
|
|
13
13
|
# @!attribute [r] hints
|
14
14
|
# @return [Array<DebugHint>] the move's hints
|
15
15
|
attr_reader :hints
|
16
|
-
|
16
|
+
|
17
17
|
# Initializer
|
18
|
-
#
|
18
|
+
#
|
19
19
|
# @param x [Integer] x-coordinate
|
20
20
|
# @param y [Integer] y-coordinate
|
21
21
|
def initialize(x, y)
|
@@ -23,7 +23,7 @@ class Move
|
|
23
23
|
@y = y
|
24
24
|
@hints = Array.new
|
25
25
|
end
|
26
|
-
|
26
|
+
|
27
27
|
# @overload addHint(hint)
|
28
28
|
# adds a hint to the move
|
29
29
|
# @param hint [DebugHint] the added hint
|
@@ -37,17 +37,17 @@ class Move
|
|
37
37
|
def addHint(hint)
|
38
38
|
@hints.push(hint);
|
39
39
|
end
|
40
|
-
|
40
|
+
|
41
41
|
# adds a hint to the move
|
42
42
|
def addHint(key, value)
|
43
43
|
self.addHint(DebugHint.new(key, value))
|
44
44
|
end
|
45
|
-
|
45
|
+
|
46
46
|
# adds a hint to the move
|
47
47
|
def addHint(string)
|
48
48
|
self.addHint(DebugHint.new(string))
|
49
49
|
end
|
50
|
-
|
50
|
+
|
51
51
|
def ==(another_move)
|
52
52
|
return self.x == another_move.x && self.y == another_move.y
|
53
53
|
end
|
@@ -12,36 +12,36 @@ class Network
|
|
12
12
|
@socket
|
13
13
|
@host
|
14
14
|
@port
|
15
|
-
|
15
|
+
|
16
16
|
@board
|
17
17
|
@client
|
18
18
|
@protocol
|
19
|
-
|
19
|
+
|
20
20
|
@receiveBuffer
|
21
21
|
@reservationID
|
22
|
-
|
22
|
+
|
23
23
|
# @!attribute [r] connected
|
24
24
|
# @return [Boolean] true, if the client is connected to a server
|
25
25
|
attr_reader :connected
|
26
|
-
|
26
|
+
|
27
27
|
def initialize(host, port, board, client)
|
28
|
-
@host, @port, @connected, @board, @client =
|
28
|
+
@host, @port, @connected, @board, @client =
|
29
29
|
host, port, false, board, client
|
30
|
-
|
30
|
+
|
31
31
|
@protocol = Protocol.new(self, @client)
|
32
32
|
@reservationID = ''
|
33
33
|
@receiveBuffer = ''
|
34
|
-
|
34
|
+
|
35
35
|
puts '> Network/Socket created.'
|
36
36
|
end
|
37
37
|
|
38
38
|
# connects the client with a given server
|
39
|
-
#
|
39
|
+
#
|
40
40
|
# @return [Boolean] true, if successfully connected to the server
|
41
41
|
def connect
|
42
42
|
@socket = TCPSocket.open(@host, @port)
|
43
43
|
@connected = true
|
44
|
-
|
44
|
+
|
45
45
|
self.sendString('<protocol>')
|
46
46
|
if @reservationID != ''
|
47
47
|
document = REXML::Docuent.new
|
@@ -49,7 +49,7 @@ class Network
|
|
49
49
|
element.add_attribute('reservationCode', @reservationID)
|
50
50
|
document.add(element)
|
51
51
|
self.sendXML(document)
|
52
|
-
else
|
52
|
+
else
|
53
53
|
document = REXML::Document.new
|
54
54
|
element = REXML::Element.new('join')
|
55
55
|
element.add_attribute('gameType', 'swc_2016_twixt')
|
@@ -58,7 +58,7 @@ class Network
|
|
58
58
|
end
|
59
59
|
return @connected
|
60
60
|
end
|
61
|
-
|
61
|
+
|
62
62
|
# disconnects the client from a server
|
63
63
|
def disconnect
|
64
64
|
|
@@ -74,10 +74,10 @@ class Network
|
|
74
74
|
def readString
|
75
75
|
puts 'reading'
|
76
76
|
sockMsg = ''
|
77
|
-
if(!@connected)
|
77
|
+
if(!@connected)
|
78
78
|
return
|
79
79
|
end
|
80
|
-
|
80
|
+
|
81
81
|
line =''
|
82
82
|
char = ''
|
83
83
|
while line!="</room>"
|
@@ -91,7 +91,7 @@ class Network
|
|
91
91
|
end
|
92
92
|
puts 'ended reading'
|
93
93
|
if sockMsg != ''
|
94
|
-
|
94
|
+
|
95
95
|
@receiveBuffer.concat(sockMsg)
|
96
96
|
|
97
97
|
# Remove <protocol> tag
|
@@ -100,7 +100,7 @@ class Network
|
|
100
100
|
puts 'Receive:'
|
101
101
|
puts ''
|
102
102
|
#puts @receiveBuffer
|
103
|
-
|
103
|
+
|
104
104
|
# Process text
|
105
105
|
@protocol.processString('<msg>'+@receiveBuffer+'</msg>');
|
106
106
|
self.emptyReceiveBuffer
|
@@ -10,16 +10,16 @@ class Player
|
|
10
10
|
# @!attribute [rw] points
|
11
11
|
# @return [Integer] the player's points
|
12
12
|
attr_accessor :points
|
13
|
-
|
13
|
+
|
14
14
|
# Initializer
|
15
15
|
# @param the new player's color
|
16
16
|
def initialize(color)
|
17
17
|
@color = color
|
18
18
|
self.points = 0
|
19
19
|
end
|
20
|
-
|
20
|
+
|
21
21
|
def ==(another_player)
|
22
22
|
return self.color == another_player.color
|
23
23
|
end
|
24
|
-
|
24
|
+
|
25
25
|
end
|
@@ -13,7 +13,7 @@ require 'rexml/streamlistener'
|
|
13
13
|
# This class handles the parsing of xml strings according to the network protocol of twixt
|
14
14
|
class Protocol
|
15
15
|
include REXML::StreamListener
|
16
|
-
|
16
|
+
|
17
17
|
# @!attribute [r] gamestate
|
18
18
|
# @return [Gamestate] current gamestate
|
19
19
|
attr_reader :gamestate
|
@@ -27,19 +27,19 @@ class Protocol
|
|
27
27
|
|
28
28
|
def initialize(network, client)
|
29
29
|
@gamestate = GameState.new
|
30
|
-
@network, @client = network, client
|
30
|
+
@network, @client = network, client
|
31
31
|
self.client.gamestate = self.gamestate
|
32
32
|
end
|
33
|
-
|
33
|
+
|
34
34
|
# starts xml-string parsing
|
35
|
-
#
|
35
|
+
#
|
36
36
|
# @param text [String] the xml-string that will be parsed
|
37
37
|
def processString(text)
|
38
38
|
list = self
|
39
39
|
#puts "Parse XML:\n#{text}\n----END XML"
|
40
40
|
REXML::Document.parse_stream(text, list)
|
41
41
|
end
|
42
|
-
|
42
|
+
|
43
43
|
# called if an end-tag is read
|
44
44
|
#
|
45
45
|
# @param name [String] the end-tag name, that was read
|
@@ -94,7 +94,7 @@ class Protocol
|
|
94
94
|
@gamestate.startPlayerColor = attrs['startPlayer'] == 'RED' ? PlayerColor::RED : PlayerColor::BLUE
|
95
95
|
@gamestate.currentPlayerColor = attrs['currentPlayer'] == 'RED' ? PlayerColor::RED : PlayerColor::BLUE
|
96
96
|
puts "Turn: #{@gamestate.turn}"
|
97
|
-
when "red"
|
97
|
+
when "red"
|
98
98
|
puts 'new red player'
|
99
99
|
@gamestate.addPlayer(Player.new(attrs['color'] == 'RED' ? PlayerColor::RED : PlayerColor::BLUE))
|
100
100
|
@gamestate.red.points = attrs['points'].to_i
|
@@ -144,7 +144,7 @@ class Protocol
|
|
144
144
|
#
|
145
145
|
# @param document [REXML::Document] the document, that will be send to the connected server
|
146
146
|
def sendXml(document)
|
147
|
-
@network.sendXML(document)
|
147
|
+
@network.sendXML(document)
|
148
148
|
end
|
149
|
-
|
149
|
+
|
150
150
|
end
|
metadata
CHANGED
@@ -1,14 +1,14 @@
|
|
1
1
|
--- !ruby/object:Gem::Specification
|
2
2
|
name: software_challenge_client
|
3
3
|
version: !ruby/object:Gem::Version
|
4
|
-
version: 0.1.
|
4
|
+
version: 0.1.3
|
5
5
|
platform: ruby
|
6
6
|
authors:
|
7
7
|
- Ralf-Tobias Diekert
|
8
8
|
autorequire:
|
9
9
|
bindir: exe
|
10
10
|
cert_chain: []
|
11
|
-
date: 2015-
|
11
|
+
date: 2015-12-08 00:00:00.000000000 Z
|
12
12
|
dependencies:
|
13
13
|
- !ruby/object:Gem::Dependency
|
14
14
|
name: bundler
|
@@ -107,7 +107,7 @@ required_rubygems_version: !ruby/object:Gem::Requirement
|
|
107
107
|
version: '0'
|
108
108
|
requirements: []
|
109
109
|
rubyforge_project:
|
110
|
-
rubygems_version: 2.
|
110
|
+
rubygems_version: 2.5.0
|
111
111
|
signing_key:
|
112
112
|
specification_version: 4
|
113
113
|
summary: This gem provides functions to build a client for the coding competition
|