Skip to content

Instantly share code, notes, and snippets.

@mgiuffrida
Created July 11, 2015 22:47
Show Gist options
  • Save mgiuffrida/98c641a331f53c8cb8b7 to your computer and use it in GitHub Desktop.
Save mgiuffrida/98c641a331f53c8cb8b7 to your computer and use it in GitHub Desktop.
Solution to intermediate epic mode - github.com/ryanb/ruby-warrior
# Total Score: 917
# Your average grade for this tower is: A
#
# Level 1: S
# Level 2: A
# Level 3: B
# Level 4: A
# Level 5: B
# Level 6: A
# Level 7: A
class Player
@@dirs = [:forward, :left, :backward, :right]
def play_turn(w)
# If surrounded, bind a warrior.
adjacentMobs = []
adjacentCaptives = []
tickingCaptives = []
@@dirs.each { |x|
if w.feel(x).enemy?
adjacentMobs.push(x)
end
if w.feel(x).captive?
adjacentCaptives.push(x)
end
}
remaining = w.listen
remaining.each { |x|
if x.ticking?
tickingCaptives.push(x)
end
}
if not tickingCaptives.empty?
dir = w.direction_of(tickingCaptives.first)
ahead = w.look(dir)
count = 0
if ahead[0].enemy? and ahead[1].enemy?
safe = true
if w.health <= 4
safe = false
else
tickingCaptives.each { |c|
if w.distance_of(c) <= 2
safe = false
break
end
}
end
if safe
acted = false
adjacentMobs.each { |e|
if e == :forward
next
end
w.bind!(e)
acted = true
break
}
if not acted
w.detonate!(dir)
end
return
end
end
end
if not remaining.empty? and adjacentMobs.empty? and w.health < 11
if tickingCaptives.empty?
w.rest!
return
else
spaces = w.look(w.direction_of(tickingCaptives.first))
if spaces[0].captive?
w.rescue!(w.direction_of(spaces[0]))
return
elsif spaces[1].enemy?
w.rest!
return
end
end
end
if tickingCaptives.length > 0
next_dir = w.direction_of(tickingCaptives.first)
if w.feel(next_dir).captive?
w.rescue!(next_dir)
elsif not w.feel(next_dir).empty? or w.feel(next_dir).stairs?
avoid_dir = avoid(w, next_dir)
if avoid_dir and avoid_dir != opposite(@last_movement)
w.walk!(avoid_dir)
@last_movement = avoid_dir
else
push_thru = next_dir
end
else
w.walk!(next_dir)
@last_movement = next_dir
end
end
if tickingCaptives.length > 0
if push_thru
deal_with(w, push_thru)
end
else
if adjacentMobs.length > 0
deal_with(w, adjacentMobs.first)
elsif not remaining.empty? and w.health < 16
w.rest!
elsif adjacentCaptives.length > 0
w.rescue!(adjacentCaptives.first)
else
if remaining.empty?
w.walk!(w.direction_of_stairs)
@last_movement = w.direction_of_stairs
else
next_dir = w.direction_of(remaining.first)
if w.feel(next_dir).stairs?
next_dir = avoid(w, next_dir)
end
w.walk!(next_dir)
@last_movement = next_dir
end
end
end
end
def deal_with(w, dir)
# Bind any other enemies.
for i in 0..@@dirs.length-1
d = @@dirs[i]
if d == dir
next
end
unit = w.feel(d)
if unit.enemy?
w.bind!(d)
return
end
end
unit = w.feel(dir)
if unit.enemy?
w.attack!(dir)
elsif unit.captive?
w.rescue!(dir)
end
end
def avoid(w, dir)
index = @@dirs.find_index(dir)
try_dir = @@dirs[(index + 1) % @@dirs.length]
if w.feel(try_dir).empty?
next_dir = try_dir
else
try_dir = @@dirs[(index + 3) % @@dirs.length]
if w.feel(try_dir).empty?
next_dir = try_dir
end
end
return next_dir
end
def opposite(dir)
if dir == :forward
return :backward
elsif dir == :backward
return :forward
elsif dir == :right
return :left
end
return :right
end
end
Sign up for free to join this conversation on GitHub. Already have an account? Sign in to comment