road_to_rubykaigi 0.2.1 → 2026.0.1
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/.road_to_rubykaigi.sample +26 -0
- data/Rakefile +1 -3
- data/examples/accelerometer.rb +131 -0
- data/lib/road_to_rubykaigi/ansi.rb +8 -0
- data/lib/road_to_rubykaigi/calibration_bar.rb +84 -0
- data/lib/road_to_rubykaigi/calibration_result.rb +70 -0
- data/lib/road_to_rubykaigi/calibration_sampler.rb +52 -0
- data/lib/road_to_rubykaigi/calibration_screen.rb +171 -0
- data/lib/road_to_rubykaigi/config.rb +164 -0
- data/lib/road_to_rubykaigi/event_dispatcher.rb +3 -0
- data/lib/road_to_rubykaigi/fireworks.rb +2 -2
- data/lib/road_to_rubykaigi/game.rb +2 -0
- data/lib/road_to_rubykaigi/game_server.rb +91 -0
- data/lib/road_to_rubykaigi/graphics/2026/map.txt +30 -0
- data/lib/road_to_rubykaigi/graphics/2026/mask.txt +30 -0
- data/lib/road_to_rubykaigi/graphics/map.rb +2 -1
- data/lib/road_to_rubykaigi/graphics/mask.rb +1 -1
- data/lib/road_to_rubykaigi/graphics/player.rb +78 -48
- data/lib/road_to_rubykaigi/graphics/player.txt +4 -0
- data/lib/road_to_rubykaigi/jump_detector.rb +125 -0
- data/lib/road_to_rubykaigi/manager/audio_manager.rb +8 -2
- data/lib/road_to_rubykaigi/manager/game_manager.rb +3 -2
- data/lib/road_to_rubykaigi/opening_screen.rb +87 -16
- data/lib/road_to_rubykaigi/score_board.rb +6 -1
- data/lib/road_to_rubykaigi/serial_reader.rb +76 -0
- data/lib/road_to_rubykaigi/signal_interpreter.rb +199 -0
- data/lib/road_to_rubykaigi/signal_window.rb +139 -0
- data/lib/road_to_rubykaigi/sprite/bonus.rb +83 -45
- data/lib/road_to_rubykaigi/sprite/deadline.rb +2 -2
- data/lib/road_to_rubykaigi/sprite/enemy.rb +28 -21
- data/lib/road_to_rubykaigi/sprite/player.rb +51 -12
- data/lib/road_to_rubykaigi/version.rb +1 -1
- data/lib/road_to_rubykaigi.rb +42 -19
- data/public/controller.html +54 -0
- data/public/controller.rb +137 -0
- data/public/init.iife.js +122 -0
- data/public/picoruby.js +2 -0
- data/public/picoruby.wasm +0 -0
- data/tmp/.keep +0 -0
- metadata +41 -8
- data/.standard.yml +0 -29
- /data/lib/road_to_rubykaigi/graphics/{demo-map.txt → 2025/demo-map.txt} +0 -0
- /data/lib/road_to_rubykaigi/graphics/{demo-mask.txt → 2025/demo-mask.txt} +0 -0
- /data/lib/road_to_rubykaigi/graphics/{map.txt → 2025/map.txt} +0 -0
- /data/lib/road_to_rubykaigi/graphics/{mask.txt → 2025/mask.txt} +0 -0
|
@@ -0,0 +1,164 @@
|
|
|
1
|
+
require 'singleton'
|
|
2
|
+
require 'forwardable'
|
|
3
|
+
|
|
4
|
+
module RoadToRubykaigi
|
|
5
|
+
class Config
|
|
6
|
+
include Singleton
|
|
7
|
+
|
|
8
|
+
CONFIG_FILE = '.road_to_rubykaigi'
|
|
9
|
+
DEFAULT_START_THRESHOLD = 0.025
|
|
10
|
+
DEFAULT_CONTINUATION_THRESHOLD = 0.05
|
|
11
|
+
|
|
12
|
+
class << self
|
|
13
|
+
extend Forwardable
|
|
14
|
+
def_delegators :instance, :input_source, :ble?, :serial?, :external_input?, :cycle_input_source,
|
|
15
|
+
:serial_port, :detect_serial_port!,
|
|
16
|
+
:signal_source, :debug?, :bgm_off?, :demo?, :project_root,
|
|
17
|
+
:start_threshold, :continuation_threshold, :walk_cadence, :walk_intensity,
|
|
18
|
+
:gravity_vector, :jump_v_max, :save_calibration
|
|
19
|
+
end
|
|
20
|
+
|
|
21
|
+
INPUT_SOURCES = %i[ble serial].freeze
|
|
22
|
+
INPUT_SOURCE_CYCLE = [nil, :ble, :serial].freeze
|
|
23
|
+
|
|
24
|
+
def initialize
|
|
25
|
+
@settings = load
|
|
26
|
+
end
|
|
27
|
+
|
|
28
|
+
def input_source
|
|
29
|
+
value = @settings['INPUT_SOURCE']&.to_sym
|
|
30
|
+
INPUT_SOURCES.include?(value) ? value : nil
|
|
31
|
+
end
|
|
32
|
+
|
|
33
|
+
def ble? = input_source == :ble
|
|
34
|
+
def serial? = input_source == :serial
|
|
35
|
+
def external_input? = !input_source.nil?
|
|
36
|
+
|
|
37
|
+
def input_source=(value)
|
|
38
|
+
@settings['INPUT_SOURCE'] = value.to_s
|
|
39
|
+
save(['INPUT_SOURCE'])
|
|
40
|
+
end
|
|
41
|
+
|
|
42
|
+
def cycle_input_source
|
|
43
|
+
current_index = INPUT_SOURCE_CYCLE.index(input_source) || 0
|
|
44
|
+
self.input_source = INPUT_SOURCE_CYCLE[(current_index + 1) % INPUT_SOURCE_CYCLE.size]
|
|
45
|
+
detect_serial_port! if serial?
|
|
46
|
+
end
|
|
47
|
+
|
|
48
|
+
def serial_port
|
|
49
|
+
@settings['SERIAL_PORT'] || detect_serial_port
|
|
50
|
+
end
|
|
51
|
+
|
|
52
|
+
def detect_serial_port!
|
|
53
|
+
return serial_port if File.exist?(serial_port)
|
|
54
|
+
|
|
55
|
+
port = detect_serial_port
|
|
56
|
+
if port
|
|
57
|
+
@settings['SERIAL_PORT'] = port
|
|
58
|
+
save(['SERIAL_PORT'])
|
|
59
|
+
end
|
|
60
|
+
port
|
|
61
|
+
end
|
|
62
|
+
|
|
63
|
+
def signal_source
|
|
64
|
+
serial? ? SerialReader : GameServer
|
|
65
|
+
end
|
|
66
|
+
|
|
67
|
+
def debug?
|
|
68
|
+
@settings['DEBUG']
|
|
69
|
+
end
|
|
70
|
+
|
|
71
|
+
def bgm_off?
|
|
72
|
+
@settings['BGM_OFF']
|
|
73
|
+
end
|
|
74
|
+
|
|
75
|
+
def demo?
|
|
76
|
+
@settings['DEMO']
|
|
77
|
+
end
|
|
78
|
+
|
|
79
|
+
def start_threshold
|
|
80
|
+
(@settings['START_THRESHOLD'] || DEFAULT_START_THRESHOLD).to_f
|
|
81
|
+
end
|
|
82
|
+
|
|
83
|
+
def continuation_threshold
|
|
84
|
+
(@settings['CONTINUATION_THRESHOLD'] || DEFAULT_CONTINUATION_THRESHOLD).to_f
|
|
85
|
+
end
|
|
86
|
+
|
|
87
|
+
def walk_cadence
|
|
88
|
+
@settings['WALK_CADENCE']&.to_f
|
|
89
|
+
end
|
|
90
|
+
|
|
91
|
+
def walk_intensity
|
|
92
|
+
@settings['WALK_INTENSITY']&.to_f
|
|
93
|
+
end
|
|
94
|
+
|
|
95
|
+
def gravity_vector
|
|
96
|
+
value = @settings['GRAVITY']
|
|
97
|
+
return nil unless value
|
|
98
|
+
|
|
99
|
+
parts = value.split(',').map(&:to_f)
|
|
100
|
+
parts.size == 3 ? parts : nil
|
|
101
|
+
end
|
|
102
|
+
|
|
103
|
+
def jump_v_max
|
|
104
|
+
@settings['JUMP_V_MAX']&.to_f
|
|
105
|
+
end
|
|
106
|
+
|
|
107
|
+
def save_calibration(start_threshold:, continuation_threshold:, walk_cadence:, walk_intensity:,
|
|
108
|
+
gravity_vector: nil, jump_v_max: nil)
|
|
109
|
+
@settings['START_THRESHOLD'] = start_threshold.to_s
|
|
110
|
+
@settings['CONTINUATION_THRESHOLD'] = continuation_threshold.to_s
|
|
111
|
+
@settings['WALK_CADENCE'] = walk_cadence.to_s
|
|
112
|
+
@settings['WALK_INTENSITY'] = walk_intensity.to_s
|
|
113
|
+
keys = %w[START_THRESHOLD CONTINUATION_THRESHOLD WALK_CADENCE WALK_INTENSITY]
|
|
114
|
+
if gravity_vector
|
|
115
|
+
@settings['GRAVITY'] = gravity_vector.join(',')
|
|
116
|
+
keys << 'GRAVITY'
|
|
117
|
+
end
|
|
118
|
+
if jump_v_max
|
|
119
|
+
@settings['JUMP_V_MAX'] = jump_v_max.to_s
|
|
120
|
+
keys << 'JUMP_V_MAX'
|
|
121
|
+
end
|
|
122
|
+
save(keys)
|
|
123
|
+
end
|
|
124
|
+
|
|
125
|
+
def project_root
|
|
126
|
+
__dir__.sub('lib/road_to_rubykaigi', '')
|
|
127
|
+
end
|
|
128
|
+
|
|
129
|
+
private
|
|
130
|
+
|
|
131
|
+
def detect_serial_port
|
|
132
|
+
Dir.glob('/dev/cu.usbserial-*').first
|
|
133
|
+
end
|
|
134
|
+
|
|
135
|
+
def config_path
|
|
136
|
+
File.join(project_root, CONFIG_FILE)
|
|
137
|
+
end
|
|
138
|
+
|
|
139
|
+
def load
|
|
140
|
+
return {} unless File.exist?(config_path)
|
|
141
|
+
|
|
142
|
+
File.readlines(config_path, chomp: true)
|
|
143
|
+
.reject { |line| line.strip.empty? || line.strip.start_with?('#') }
|
|
144
|
+
.each_with_object({}) do |line, hash|
|
|
145
|
+
key, value = line.split('=', 2)
|
|
146
|
+
hash[key.strip] = value.strip if value
|
|
147
|
+
end
|
|
148
|
+
end
|
|
149
|
+
|
|
150
|
+
def save(keys)
|
|
151
|
+
File.copy_stream("#{config_path}.sample", config_path) unless File.exist?(config_path)
|
|
152
|
+
|
|
153
|
+
lines = File.readlines(config_path, chomp: true)
|
|
154
|
+
keys.each do |key|
|
|
155
|
+
pattern = /\A\s*#?\s*#{key}\s*=/
|
|
156
|
+
entry = "#{key}=#{@settings[key]}"
|
|
157
|
+
index = lines.index { |line| line.match?(pattern) }
|
|
158
|
+
index ? lines[index] = entry : lines << entry
|
|
159
|
+
lines.reject! { |line| line.match?(pattern) && line != entry }
|
|
160
|
+
end
|
|
161
|
+
File.write(config_path, lines.join("\n") + "\n")
|
|
162
|
+
end
|
|
163
|
+
end
|
|
164
|
+
end
|
|
@@ -52,12 +52,15 @@ module RoadToRubykaigi
|
|
|
52
52
|
return if @player.stunned?
|
|
53
53
|
|
|
54
54
|
case action
|
|
55
|
+
when SignalInterpreter::Walk
|
|
56
|
+
@player.walk(action)
|
|
55
57
|
when :jump; @player.jump
|
|
56
58
|
when :crouch
|
|
57
59
|
@player.crouch
|
|
58
60
|
Manager::AudioManager.instance.crouch
|
|
59
61
|
when :right; @player.right
|
|
60
62
|
when :left; @player.left
|
|
63
|
+
when :stop; @player.stop
|
|
61
64
|
when :attack
|
|
62
65
|
if @player.can_attack?(@attacks)
|
|
63
66
|
@player.attack(@attacks)
|
|
@@ -1,6 +1,6 @@
|
|
|
1
1
|
module RoadToRubykaigi
|
|
2
2
|
class Fireworks
|
|
3
|
-
START_X = 632
|
|
3
|
+
START_X = { 2025 => 632, 2026 => 782 }
|
|
4
4
|
DEMO_START_X = 524
|
|
5
5
|
DURATION_SECOND = 0.1
|
|
6
6
|
|
|
@@ -39,7 +39,7 @@ module RoadToRubykaigi
|
|
|
39
39
|
private
|
|
40
40
|
|
|
41
41
|
def initialize
|
|
42
|
-
@x = RoadToRubykaigi.demo? ? DEMO_START_X : START_X
|
|
42
|
+
@x = RoadToRubykaigi.demo? ? DEMO_START_X : START_X[RoadToRubykaigi.version]
|
|
43
43
|
@y = 3
|
|
44
44
|
@start_time = Time.now
|
|
45
45
|
@frame_index = 0
|
|
@@ -8,6 +8,7 @@ module RoadToRubykaigi
|
|
|
8
8
|
loop do
|
|
9
9
|
RoadToRubykaigi.debug.clear
|
|
10
10
|
process_input($stdin.read_nonblock(4, exception: false))
|
|
11
|
+
SignalInterpreter.process
|
|
11
12
|
|
|
12
13
|
if @game_manager.result?
|
|
13
14
|
print(@game_manager.render_result)
|
|
@@ -63,6 +64,7 @@ module RoadToRubykaigi
|
|
|
63
64
|
attacks: attacks, bonuses: bonuses, effects: effects, enemies: enemies, player: player, game_manager: @game_manager,
|
|
64
65
|
)
|
|
65
66
|
Manager::AudioManager.instance
|
|
67
|
+
Config.signal_source.start if Config.external_input?
|
|
66
68
|
end
|
|
67
69
|
|
|
68
70
|
def process_input(input)
|
|
@@ -0,0 +1,91 @@
|
|
|
1
|
+
require 'singleton'
|
|
2
|
+
require 'webrick'
|
|
3
|
+
|
|
4
|
+
module RoadToRubykaigi
|
|
5
|
+
class GameServer
|
|
6
|
+
include Singleton
|
|
7
|
+
|
|
8
|
+
HOST = 'http://127.0.0.1'
|
|
9
|
+
PORT = 2026
|
|
10
|
+
ENDPOINT = '/road_to_rubykaigi'
|
|
11
|
+
MAX_AGE_SECONDS = 0.5
|
|
12
|
+
|
|
13
|
+
class << self
|
|
14
|
+
extend Forwardable
|
|
15
|
+
def_delegators :instance, :start, :queue, :drain, :open_controller
|
|
16
|
+
end
|
|
17
|
+
|
|
18
|
+
attr_reader :queue
|
|
19
|
+
|
|
20
|
+
def drain
|
|
21
|
+
now = Time.now.to_f
|
|
22
|
+
until @queue.empty?
|
|
23
|
+
data = @queue.pop(true)
|
|
24
|
+
t_ms = data['t']
|
|
25
|
+
next if t_ms && now - t_ms.to_f / 1000.0 > MAX_AGE_SECONDS
|
|
26
|
+
yield data
|
|
27
|
+
end
|
|
28
|
+
rescue ThreadError
|
|
29
|
+
# pop(true) raises if the queue empties mid-drain
|
|
30
|
+
end
|
|
31
|
+
|
|
32
|
+
def start
|
|
33
|
+
@queue.clear
|
|
34
|
+
return if @server
|
|
35
|
+
|
|
36
|
+
@server = build_server
|
|
37
|
+
@thread = Thread.new { @server.start }
|
|
38
|
+
at_exit do
|
|
39
|
+
@server.shutdown rescue nil
|
|
40
|
+
@thread.kill
|
|
41
|
+
end
|
|
42
|
+
open_controller unless Config.demo?
|
|
43
|
+
end
|
|
44
|
+
|
|
45
|
+
def open_controller
|
|
46
|
+
url = "#{HOST}:#{PORT}/controller.html"
|
|
47
|
+
command =
|
|
48
|
+
case RbConfig::CONFIG['host_os']
|
|
49
|
+
when /darwin/ then ['open', url]
|
|
50
|
+
when /mswin|mingw|cygwin/ then ['cmd', '/c', 'start', '', url]
|
|
51
|
+
else ['xdg-open', url]
|
|
52
|
+
end
|
|
53
|
+
pid = spawn(*command, out: File::NULL, err: File::NULL)
|
|
54
|
+
Process.detach(pid)
|
|
55
|
+
rescue
|
|
56
|
+
# best effort: don't crash the server if the browser can't be opened
|
|
57
|
+
end
|
|
58
|
+
|
|
59
|
+
private
|
|
60
|
+
|
|
61
|
+
def initialize
|
|
62
|
+
@queue = Thread::Queue.new
|
|
63
|
+
log_file = Config.debug? ? File.join(Config.project_root, 'tmp/game_server.log') : File.open(File::NULL, 'w')
|
|
64
|
+
@logger = WEBrick::Log.new(log_file)
|
|
65
|
+
end
|
|
66
|
+
|
|
67
|
+
def build_server
|
|
68
|
+
server = WEBrick::HTTPServer.new(
|
|
69
|
+
Port: PORT,
|
|
70
|
+
Logger: @logger,
|
|
71
|
+
AccessLog: [],
|
|
72
|
+
)
|
|
73
|
+
server.mount_proc(ENDPOINT) { |req, res| handle(req, res) }
|
|
74
|
+
|
|
75
|
+
public_dir = File.join(Config.project_root, 'public')
|
|
76
|
+
server.mount('/', WEBrick::HTTPServlet::FileHandler, public_dir)
|
|
77
|
+
|
|
78
|
+
server
|
|
79
|
+
end
|
|
80
|
+
|
|
81
|
+
def handle(req, res)
|
|
82
|
+
res['Access-Control-Allow-Origin'] = '*'
|
|
83
|
+
res['Access-Control-Allow-Methods'] = 'GET, OPTIONS'
|
|
84
|
+
|
|
85
|
+
@logger.info("#{req.request_method} #{req.path} #{req.query}")
|
|
86
|
+
@queue.push(req.query) unless req.query.empty?
|
|
87
|
+
|
|
88
|
+
res.status = 200
|
|
89
|
+
end
|
|
90
|
+
end
|
|
91
|
+
end
|
|
@@ -0,0 +1,30 @@
|
|
|
1
|
+
┌──────────────────────────────────────────────────────────────────────────────────────────┬──────────────────────────────────────────────────┬────────────────────────────────────────────────┬────────────────────────────────────────────────────────────────────────────────────────────────────────────────────────────────────────────────────────────────────────────────────────────────────────────────────────────────────────────────────────────────────────────────────────────────────────────────────────────────────────────────────────────────────────────────────────────────────────────────────────────────────────────────────────────────────────────────────────────────────────────────────────────────────────────────────────────────────────────────────────────────────────────────────────────────────────────────────────────────────────────────────────────────────────────────────────────────────────────────────────────────────────────┐
|
|
2
|
+
│ │ │ │ ⣰⣾⣆ │
|
|
3
|
+
│ │ │ │ ⣰⣴⣾⣿⣷⣆ │
|
|
4
|
+
│ ┌──────────────────────────────────────────────┐ .─┴─. .─┴─. .─┴─. ⣰⣾⣾⣿⣿⣿⣿⣆ ⣀⣰⣿⣿⣿⣿⣿⣿⣿⣆ │
|
|
5
|
+
│ │ │ ( ) ( ) ( ) ⣰⣾⣾⣾⣾⡀⣾⣾⣾⣾⣾⣷⣄ ⢀⣰⣾⣿⣿⣿⣿⣿⣿⣿⣿⣿⣆⡀ │
|
|
6
|
+
│ │ Walk with ← → key │ '───' '───' '───' ⢀⣰⣾⣾⣾⣾⣾⣾⣾⣾⣾⣾⣾⣾⣾⣾⣾⣷⣄ ⢀⣾⣿⣿⣿⣿⣿⣿⣿⣿⣿⣿⣿⣿⣿⣆ │
|
|
7
|
+
│ │ Jump with ↑ key │ ⣰⣾⣾⣾⣾⣾⣾⣾⣾⣾⣾⣾⣾⣾⣾⣾⣾⣾⣾⣾⣾⣿⣷⣄ ⢀⣀⣀⣀⣀⣀⣠⣤⣤⣤⣴⣾⣿⣿⣿⣿⣿⣿⣿⣿⣿⣿⣿⣿⣿⣿⣿⣿⣿⣿⣷⣦⡀ ╔═══════╗ ║ ║ │
|
|
8
|
+
│ │ Stomp bugs for bonus │ ⢀⣰⣾⣾⣾⣾⣾⣾⣾⣾⣾⣾⣾⣾⣾⣾⣾⣾ ⣾⣾⣾⣾⣾⣾⣾⣾⣾⣷⣄ ⠈⢿⣿⣿⣿⣿⣿⣿⣿⣿⣿⣿⣿⣿⣿⣿⣿⣿⣿⣿⣿⣿⣿⣿⣿⣿⣿⣿⣿⣿⣿⣿⣿⣿⣿⣿⣿⣾⣿⣾⣾⣷⣦⣄ ║ ║ ║ ║ │
|
|
9
|
+
│ │ Bumping into bugs stuns you │ ┌────────────────────────────────────────────────────────────────────────────────────────────────────────────────────────────────────────────────────────────────────────┐ ⣴⣿⣿⣷⣾⣿⣿⣆ ⣰⣾⣾⣾⣾⣾⣾ ⣾⣾⣾⣾⣾⣾⣾⣾⣾ ⣾⣾⣾⣾⣾ ⣾⣾⣾⣾⣾⣾⣾⣾⣾⣾⣶⣄⡀ ⠈⠹⣿⣿⣿⣿⣿⣿⣿⣿⣿⣿⣿⣿⣿⣿⣿⣿⣿⣿⣿⣿⣿⣿⣿⣿⣿⣿⣿⣿⣿⣿⣿⣿⣿⣿⣿⣾⣿⣿⣿⣿⣾⣷⣷⣄⡀ ║ ║ ║ ║ ║ ║ ║ ╔═══════║ │
|
|
10
|
+
│ │ │ │ ⡔⣭⣶⣿⣿⣿⣿⣿⣿⣮⣔⢄ │ ⢀⣴⣄ ⢾⣿⡿⢿⣿⣿⣿⠟ ⢀⣰⣾⣾⣾⣾⣾⣾ ⠟ ⡞ ⣾ ⣾⣾ ⣾⣾⣾⣾⣾ ⣾⣾⣾⣾⣾ ⣾⣾⣾⣾⣷⣄ ⣿⣿⣿⣿⣿⣿⣿⣿⣿⣿⣿⣿⣿⣿⣿⣿⣿⣿⣿⣿⣿⣿⣿⣿⣿⣿⣿⣿⣿⣿⣿⣿⣿⣿⣿⣿⣿⣿⣿⣿⣿⣿⣿⣿⣿⣿⣷⣄⣀⣀ ║ ║ ║ ║ ║ ║ ║ ║ ║ ║ ║ │
|
|
11
|
+
│ │ Escape the deadline to attend RubyKaigi! │ │ ⠴⡟⣰⣷⣭⠛⠿⠿⣿⣿⠿⠿⣛⣵⡇⣦⣆ ╔══════╗ ═══╦═══ ╔══════╗ ╔═════╗ ═══╦═══ ║║ ║║ ⢀⣰⣧⡀ │ ⣰⣿⣿⣿⣧⡀ ⢀⣰⣾⣾⣾⣾⣾⣾⣾⠟ ⡞ ⣾ ⣾⣾⣾ ⣾ ⠈⠻⣾⣷⣦⣄ ⠈⣿⣿⣿⣿⣿⣿⣿⣿⣿⣿⣿⣿⣿⣿⣿⣿⣿⣿⣿⣿⣿⣿⣿⣿⣿⣿⣿⣿⣿⣿⣿⣿⣿⣿⣿⣿⣿⣿⣿⣿⣿⣿⣿⣿⣿⣿⣿⣿⣿⣿⣷⣄⡀ ╠═════╦═╝ ║ ║ ╠══════╗ ║ ║ ╠═════╦═╝ ╔═══════║ ║ ║ │
|
|
12
|
+
│ │ │ │ ⢀⣰⣧⡀ ⠸⣿⢠⠿⠋⣠⣶⠹⣿⣿⣿⡟⣤⠙⢿⡇⢿⣿⣿ ║ ║ ║ ║ ║ ║ ║ ║ ║║ ║║ ⠏⠙ │ ⢤⣶⣶⣿⣿⣿⣿⣿⣿⣿⣿⣿⣶⡤ ┌──────────┐ ╔═══════╗ ⢀⣰⣾⣾⠟ ⠟ ⣾⡞ ⡌⢿⣷⣄ ⢻⣿⣿⣿⣿⣿⣿⣿⣿⣿⣿⣿⣿⣿⣿⣿⣿⣿⣿⣿⣿⣿⣿⣿⣿⣿⣿⣿⣿⣿⣿⣿⣿⣿⣿⣿⣿⣿⣿⣿⣿⣿⣿⣿⣿⣿⣿⣿⣿⣿⠟⠁ ║ ╚═╗ ║ ║ ║ ╚╗ ╚═══════╣ ║ ╚═╗ ║ ║ ║ ╚═══════╣ ║ │
|
|
13
|
+
│ └──────────────────────────────────────────────┘ │ ⠙⣿⣿⣿⣿⠋ ⠻⡠⣾⣿⣿⣿⣧⠹⣿⡿⢠⣿⣿⣶⡈⢸⡿⠁ ⢀⣰⣧⡀ ║ ║ ║ ║ ║ ║ ║ ║║ ║║ │ ⠹⣿⣿⣿⣿⣿⣿⣿⣿⣿⠏ │ □ □ □ □ │ ║ ║ ⣀⣾⣾⣾⠟ ⡞ ⠈⢿⣷⣄ ⠈⣿⣿⣿⣿⣿⣿⣿⣿⣿⣿⣿⣿⣿⣿⡿⠋ ⠹⣿⣿⣿⣿⣿⣿⣿⣿⣿⣿⣿⣿⣿⣿⣿⣿⣿⣿⣿⣿⠟⠁ ║ ║ ║ ║ ║ ║ ║ ║ ║ ║ ║ ║ ║ ║ │
|
|
14
|
+
│ │ ⡿⠋⠙⢿ ⠈⠲⣤⣉⠙⠛⠂⠙⠰⠿⠛⠛⣉⡠⠂ ⠏⠙ ⢀⣰⣧⡀ ╚══════╗ ║ ╠══════╣ ╠═══╦═╝ ║ ║║ ║║ ⢀⣰⣧⡀ │ ⢨⣿⣿⣿⣿⣿⣿⣿⡅ │ │ ║ ║ ║ ⢀⣰⣾⣾⣾⣾⠟ ⠈⠻⣦ ⠙⣿⣿⣿⣿⣿⣿⣿⣿⣿⣿⣿⡿⠋ ⠹⣿⣿⣿⣿⣿⣿⣿⣿⣿⣿⣿⣿⣿⣿⣿⣿⠟ ║ ║ ╚═══════║ ╚═══════╝ ════════╝ ║ ║ ╚═══════║ ║ ════════╝ ║ │
|
|
15
|
+
│ │ ⠈⠻⣿⣿⣿⣿⣿⣿⣟⠟⠋ ⠙⣿⣿⣿⣿⠋ ║ ║ ║ ║ ║ ╚═╗ ║ ⠏⠙ │ ⣾⣿⣿⣿⣿⣿⣿⣿⣷ └──────────┘ ║ ║ ║ ⢀⣰⣾⣾⣾⣾⠟ ⠈⠻⣷⣦⣄ ⣿⣿⣿⣿⣿⣿⣿⣿⣿⣿⣏ ⣹⣿⣿⣿⣿⣿⣿⣿⣿⣿⣿⣿⣿⣿⠋ │
|
|
16
|
+
│ │ ⠈⠻⢿⡿⠋ ⡿⠋⠙⢿ ╚══════╝ ║ ║ ║ ║ ║ ║ ║║ ║║ │ ⠈⠉ ⠉⠁ ╠═════╦═╝ ╔═══════╗ ╔═══════║ ╔══════╣ ⣀⣀⣀⣀⣀⠤⣾⣾⣾⠟ ⠈⠻⣷⣦⣄ ⣸⣿⣿⣿⣿⣿⣿⣿⣿⣿⣿⣷⣆ ⣰⣾⣿⣿⣿⣿⣿⣿⣿⣿⣿⣿⣿⣿⠋ │
|
|
17
|
+
│ └────────────────────────────────────────────────────────────────────────────────────────────────────────────────────────────────────────────────────────────────────────┘ ║ ╚═╗ ║ ║ ║ ║ ╔╝ ║ ╭───────────⣶⣶⣶⣶⣶⣶⣶⣶⣶──────────────────────────────────────────────────────────────────────────────────────────────────────────────────────────────────────────────────────────────────────────────────────────────────────────────────────────────────────────────────────────┬───────────────────────────────╮ │
|
|
18
|
+
│ ┌────────┐ ║ ║ ║ ║ ║ ║ ║ ║ │ ⣿⣿⣿⣿⣿⣿⣿⣿⣿ │ ╭─┼─╮ │
|
|
19
|
+
│ │ │ ║ ║ ╚═══════╝ ╚═══════║ ╚═══════╝ │ ⣿⣿⣿⣿⣿⣿⣿⣿⣿ │ ╭──╯ │ ╰─╮ ╭▄─▄─▄─▄─▄─▄─▄─▄─▄─▄─▄─▄─▄─▄─▄─▄─▄─▄─▄─▄─▄─▄─▄─▄─▄─▄─▄─▄─▄─▄─▄─▄╮ ╭▄─▄─▄─▄─▄─▄─▄─▄─▄─▄─▄─▄─▄─▄╮ │
|
|
20
|
+
│ │ │ ┌──────────┐ ╞═══════════⣿⣿⣿⣿⣿⣿⣿⣿⣿══════════════════════════════════════════════════════════════════════════════════════════════════════════════════════════════════════════════════════════════════════════════════════════════════════════════════════════════════════════════════════════╡ ╭─╯ ╭─╯ ╰─╮ ├▀─▀─▀─▀─▀─▀─▀─▀─▀─▀─▀─▀─▀─▀─▀─▀─▀─▀─▀─▀─▀─▀─▀─▀─▀─▀─▀─▀─▀─▀─▀─▀┤ ├▀─▀─▀─▀─▀─▀─▀─▀─▀─▀─▀─▀─▀─▀┤ │
|
|
21
|
+
│ ████████ ┌──────────┐ │ │ │ □ □ □ □ │ │ ⣿⣿⣿⣿⣿⣿⣿⣿⣿ ⣠⣤⣤⣤⣤⣄ ⣠⣤⣤⣤⣤⣄ ⣠⣤⣤⣤⣤⣄ ⣠⣤⣤⣤⣤⣄ ⣠⣤⣤⣤⣤⣄ ⣠⣤⣤⣤⣤⣄ ⣠⣤⣤⣤⣤⣄ ⣠⣤⣤⣤⣤⣄ ⣠⣤⣤⣤⣤⣄ ⣠⣤⣤⣤⣤⣄ ⣠⣤⣤⣤⣤⣄ ⣠⣤⣤⣤⣤⣄ │ ╭─╯ ╭─╯ ╰─╮ │ │ │ │ │
|
|
22
|
+
│ ████████ ▓░ │ □ □ □ □ │ │ │ │ │ │ ⣿⣿⣿⣿⣿⣿⣿⣿⣿⠀⠀⠀⠀⠀ ⣿⣿⣿⣿⣿⣿ ⣿⣿⣿⣿⣿⣿ ⣿⣿⣿⣿⣿⣿ ⣿⣿⣿⣿⣿⣿ ⣿⣿⣿⣿⣿⣿ ⣿⣿⣿⣿⣿⣿ ⣿⣿⣿⣿⣿⣿ ⣿⣿⣿⣿⣿⣿ ⣿⣿⣿⣿⣿⣿ ⣿⣿⣿⣿⣿⣿ ⣿⣿⣿⣿⣿⣿ ⣿⣿⣿⣿⣿⣿ ⣶⣶⣶⣶⣶⣶⣶⣶⣶ │ ╭──╯ ╭──╯ ╰─╮ │ ○ ○ ○ ○ ○ ○ ○ ○ ○ │ │ ○ ○ ○ ○ ○ │ │
|
|
23
|
+
│ ╭─╮ ▀▀▀▜▛▀▀▀ █ ▓░ ╭────────┬────────╮ ┌──────────┐ │ │ ┌──────────┐ │ │ ┌──────────┐ └──────────┘ │ ⣿⣿⣿⣿⣿⣿⣿⣿⣿ ⣿⣿⣿⣿⣿⣿ ⣿⣿⣿⣿⣿⣿ ⣿⣿⣿⣿⣿⣿ ⣿⣿⣿⣿⣿⣿ ⣿⣿⣿⣿⣿⣿ ⣿⣿⣿⣿⣿⣿ ⣿⣿⣿⣿⣿⣿ ⣿⣿⣿⣿⣿⣿ ⣿⣿⣿⣿⣿⣿ ⣿⣿⣿⣿⣿⣿ ⣿⣿⣿⣿⣿⣿ ⣿⣿⣿⣿⣿⣿ ⣿⣿⣿⣿⣿⣿⣿⣿⣿ │ ╰────╯ ╭┴─╮ ╭─┴───────────────────────────────────────────────────────────────┤ ├───────────────────────────┴╮ │
|
|
24
|
+
│ │ │╭───╮ ═╦═══════════════▝▘═══════════╦═ ╭──┤ + + │ + + ├──╮ │ □ □ □ □ │ └──────────┘ │ □ □ □ □ │ ══╦═════════════════╦══ │ ◯ │ │ □ □ □ □ │ │ ⢿⣿⣿⣿⣿⣿⣿⣿⡿ ⢿⣿⣿⣿⣿⡿ ⢿⣿⣿⣿⣿⡿ ⢿⣿⣿⣿⣿⡿ ⢿⣿⣿⣿⣿⡿ ⢿⣿⣿⣿⣿⡿ ⢿⣿⣿⣿⣿⡿ ⢿⣿⣿⣿⣿⡿ ⢿⣿⣿⣿⣿⡿ ⢿⣿⣿⣿⣿⡿ ⢿⣿⣿⣿⣿⡿ ⢿⣿⣿⣿⣿⡿ ⢿⣿⣿⣿⣿⡿ ⣿⣿⣿⣿⣿⣿⣿⣿⣿ │ ╭─╯ ╰─╮ ├╥─╥─╥─╥─╥─╥─╥─╥─╥─╥─╥─╥─╥─╥─╥─╥─╥─╥─╥─╥─╥─╥─╥─╥─╥─╥─╥─╥─╥─╥─╥─╥─╥┴╥─╥─╥─╥─╥─╥┴╥─╥─╥─╥─╥─╥─╥─╥─╥─╥─╥─╥─╥─╥─┤ │
|
|
25
|
+
│ │ ├┴───┴───────────────────╮ ║ ║ │ │ │ │ │ ┌──────────┐ │ │ │ │ ║ ║ │ │ ┌──────────┐ │ │ │ ⠀ ⣿⣿⣿⣿⣿⣿⣿⣿⣿ │ ╭─╯ ╰─╮ │║ ║ ║ ║ ║ ║ ║ ║ ║ ║ ║ ║ ║ ║ ║ ║ ║ ║ ║ ║ ║ ║ ║ ║ ║ ║ ║ ║ ║ ║ ║ ║ ║ ║ ║ ║ ║ ║ ║ ║ ║ ║ ║ ║ ║ ║ ║ ║ ║ ║ ║ ║ ║ │ │
|
|
26
|
+
│ │ ╰────────────────────────┴╮ ║ ║ │ ╰────────┴────────╯ │ │ □ □ □ □ │ └──────────┘ └──────────┘ ║ ║ │ │ │ □ □ □ □ │ └──────────┘ │ ⠀ ⣿⣿⣿⣿⣿⣿⣿⣿⣿ │ ╭─╯ │ ╭─┴╨─╨─╨─╨─╨─╨─╨─╨─╨─╨─╨─╨─╨─╨─╨─╨─╨─╨─╨─╨─╨─╨─╨─╨─╨─╨─╨─╨─╨─╨─╨─╨─╨─╨─╨─╨─╨─╨─╨─╨─╨─╨─╨─╨─╨─╨─╨─╨─╨─╨─╨─╨─╨─┤ │
|
|
27
|
+
│ │ ╭───────────────────────╮ │ ║ ║ ╰──┬─┬─────────────┬─┬──╯ │ │ ║ ║ │ │ │ │ │ ⠀⠀⠀⠀⠀⠀⠀ ⣿⣿⣿⣿⣿⣿⣿⣿⣿ │ ╭─╯ │ ├─▄─▄┐ ┌▄─▄─▄─▄─▄─▄─▄┐ ┌▄─▄─▄─▄─▄─▄─▄─▄┐ ┌▄─▄─▄─▄─▄─▄─▄┐ ▄▄▄▄▄▄▄ ┌▄─▄─▄─▄─▄─▄┐ ┌▄─▄─▄─▄─┤ │
|
|
28
|
+
│ ╰─╯ ╰─╯ ╨ ╨ ╰─╯ ╰─╯ └──────────┘ ╨ ╨ │ │ └──────────┘ ╰────────────────────────────────────────────────────────────────────────────────────────────────────────────────────────────────────────────────────────────────────────────────────────────────────────────────────────────────────────────────────────────────⠛⠛⠛⠛⠛⠛⠛⠛⠛─────┴────────────────────────────────┴──────────────╯ ├──▀─▘ ▝─▀─▀─▀─▀─▀─▀─▘ ▝─▀─▀─▀─▀─▀─▀─▀─▘ ▝─▀─▀─▀─▀─▀─▀─▘ ███████ ▝─▀─▀─▀─▀─▀─▘ ▝─▀─▀─▀─▀┤ │
|
|
29
|
+
│ └────────┘ ╰─────────────────────────────────────────────────────────────────────▀▀▀▀▀▀▀▀▀──────────────────────────────╯ │
|
|
30
|
+
└───────────────────────────────────────────────────────────────────────────────────────────────────────────────────────────────────────────────────────────────────────────────────────────────────────────────────────────────────────────────────────────────────────────────────────────────────────────────────────────────────────────────────────────────────────────────────────────────────────────────────────────────────────────────────────────────────────────────────────────────────────────────────────────────────────────────────────────────────────────────────────────────────────────────────────────────────────────────────────────────────────────────────────────────────────────────────────────────────────────────────────────────────────────────────────────────────────────────────────────────────────────────────────────────────────────────────────────────────────────────────────────────────────────────────────────────────────────┘
|
|
@@ -0,0 +1,30 @@
|
|
|
1
|
+
┌##########################################################################################┬##################################################┬################################################┬############################################################################################################################################################################################################################################################################################################################################################################################################################################################################################################################################################################################################################################################################################################################################################################┐
|
|
2
|
+
│ │ │ │ ⣰⣾⣆ │
|
|
3
|
+
│ │ │ │ ⣰⣴⣾⣿⣷⣆ │
|
|
4
|
+
│ ┌##############################################┐ .#┴#. .#┴#. .#┴#. ⣰⣾⣾⣿⣿⣿⣿⣆ ⣀⣰⣿⣿⣿⣿⣿⣿⣿⣆ │
|
|
5
|
+
│ │ │ ( ) ( ) ( ) ⣰⣾⣾⣾⣾⡀⣾⣾⣾⣾⣾⣷⣄ ⢀⣰⣾⣿⣿⣿⣿⣿⣿⣿⣿⣿⣆⡀ │
|
|
6
|
+
│ │ Walk with ← → key │ '###' '###' '###' ⢀⣰⣾⣾⣾⣾⣾⣾⣾⣾⣾⣾⣾⣾⣾⣾⣾⣷⣄ ⢀⣾⣿⣿⣿⣿⣿⣿⣿⣿⣿⣿⣿⣿⣿⣆ │
|
|
7
|
+
│ │ Jump with ↑ key │ ⣰⣾⣾⣾⣾⣾⣾⣾⣾⣾⣾⣾⣾⣾⣾⣾⣾⣾⣾⣾⣾⣿⣷⣄ ⢀⣀⣀⣀⣀⣀⣠⣤⣤⣤⣴⣾⣿⣿⣿⣿⣿⣿⣿⣿⣿⣿⣿⣿⣿⣿⣿⣿⣿⣿⣷⣦⡀ ╔═══════╗ ║ ║ │
|
|
8
|
+
│ │ Stomp bugs for bonus │ ⢀⣰⣾⣾⣾⣾⣾⣾⣾⣾⣾⣾⣾⣾⣾⣾⣾⣾ ⣾⣾⣾⣾⣾⣾⣾⣾⣾⣷⣄ ⠈⢿⣿⣿⣿⣿⣿⣿⣿⣿⣿⣿⣿⣿⣿⣿⣿⣿⣿⣿⣿⣿⣿⣿⣿⣿⣿⣿⣿⣿⣿⣿⣿⣿⣿⣿⣿⣾⣿⣾⣾⣷⣦⣄ ║ ║ ║ ║ │
|
|
9
|
+
│ │ Bumping into bugs stuns you │ ┌########################################################################################################################################################################┐ ⣴⣿⣿⣷⣾⣿⣿⣆ ⣰⣾⣾⣾⣾⣾⣾ ⣾⣾⣾⣾⣾⣾⣾⣾⣾ ⣾⣾⣾⣾⣾ ⣾⣾⣾⣾⣾⣾⣾⣾⣾⣾⣶⣄⡀ ⠈⠹⣿⣿⣿⣿⣿⣿⣿⣿⣿⣿⣿⣿⣿⣿⣿⣿⣿⣿⣿⣿⣿⣿⣿⣿⣿⣿⣿⣿⣿⣿⣿⣿⣿⣿⣿⣾⣿⣿⣿⣿⣾⣷⣷⣄⡀ ║ ║ ║ ║ ║ ║ ║ ╔═══════║ │
|
|
10
|
+
│ │ │ │ ⡔⣭⣶⣿⣿⣿⣿⣿⣿⣮⣔⢄ │ ⢀⣴⣄ ⢾⣿⡿⢿⣿⣿⣿⠟ ⢀⣰⣾⣾⣾⣾⣾⣾ ⠟ ⡞ ⣾ ⣾⣾ ⣾⣾⣾⣾⣾ ⣾⣾⣾⣾⣾ ⣾⣾⣾⣾⣷⣄ ⣿⣿⣿⣿⣿⣿⣿⣿⣿⣿⣿⣿⣿⣿⣿⣿⣿⣿⣿⣿⣿⣿⣿⣿⣿⣿⣿⣿⣿⣿⣿⣿⣿⣿⣿⣿⣿⣿⣿⣿⣿⣿⣿⣿⣿⣿⣷⣄⣀⣀ ║ ║ ║ ║ ║ ║ ║ ║ ║ ║ ║ │
|
|
11
|
+
│ │ Escape the deadline to attend RubyKaigi! │ │ ⠴⡟⣰⣷⣭⠛⠿⠿⣿⣿⠿⠿⣛⣵⡇⣦⣆ ╔═════╗ ═══╦═══ ╔══════╗ ╔═════╗ ═══╦═══ ║║ ║║ ⢀⣰⣧⡀ │ ⣰⣿⣿⣿⣧⡀ ⢀⣰⣾⣾⣾⣾⣾⣾⣾⠟ ⡞ ⣾ ⣾⣾⣾ ⣾ ⠈⠻⣾⣷⣦⣄ ⠈⣿⣿⣿⣿⣿⣿⣿⣿⣿⣿⣿⣿⣿⣿⣿⣿⣿⣿⣿⣿⣿⣿⣿⣿⣿⣿⣿⣿⣿⣿⣿⣿⣿⣿⣿⣿⣿⣿⣿⣿⣿⣿⣿⣿⣿⣿⣿⣿⣿⣿⣷⣄⡀ ╠═════╦═╝ ║ ║ ╠══════╗ ║ ║ ╠═════╦═╝ ╔═══════║ ║ ║ │
|
|
12
|
+
│ │ │ │ ⢀⣰⣧⡀ ⠸⣿⢠⠿⠋⣠⣶⠹⣿⣿⣿⡟⣤⠙⢿⡇⢿⣿⣿ ║ ║ ║ ║ ║ ║ ║ ║ ║║ ║║ ⠏⠙ │ ⢤⣶⣶⣿⣿⣿⣿⣿⣿⣿⣿⣿⣶⡤ ############ ╔═══════╗ ⢀⣰⣾⣾⠟ ⠟ ⣾⡞ ⡌⢿⣷⣄ ⢻⣿⣿⣿⣿⣿⣿⣿⣿⣿⣿⣿⣿⣿⣿⣿⣿⣿⣿⣿⣿⣿⣿⣿⣿⣿⣿⣿⣿⣿⣿⣿⣿⣿⣿⣿⣿⣿⣿⣿⣿⣿⣿⣿⣿⣿⣿⣿⣿⣿⠟⠁ ║ ╚═╗ ║ ║ ║ ╚╗ ╚═══════╣ ║ ╚═╗ ║ ║ ║ ╚═══════╣ ║ │
|
|
13
|
+
│ └##############################################┘ │ ⠙⣿⣿⣿⣿⠋ ⠻⡠⣾⣿⣿⣿⣧⠹⣿⡿⢠⣿⣿⣶⡈⢸⡿⠁ ⢀⣰⣧⡀ ║ ║ ║ ║ ║ ║ ║ ║║ ║║ │ ⠹⣿⣿⣿⣿⣿⣿⣿⣿⣿⠏ ############ ║ ║ ⣀⣾⣾⣾⠟ ⡞ ⠈⢿⣷⣄ ⠈⣿⣿⣿⣿⣿⣿⣿⣿⣿⣿⣿⣿⣿⣿⡿⠋ ⠹⣿⣿⣿⣿⣿⣿⣿⣿⣿⣿⣿⣿⣿⣿⣿⣿⣿⣿⣿⣿⠟⠁ ║ ║ ║ ║ ║ ║ ║ ║ ║ ║ ║ ║ ║ ║ │
|
|
14
|
+
│ │ ⡿⠋⠙⢿ ⠈⠲⣤⣉⠙⠛⠂⠙⠰⠿⠛⠛⣉⡠⠂ ⠏⠙ ⢀⣰⣧⡀ ╚═════╗ ║ ╠══════╣ ╠═══╦═╝ ║ ║║ ║║ ⢀⣰⣧⡀ │ ⢨⣿⣿⣿⣿⣿⣿⣿⡅ ## ## ║ ║ ║ ⢀⣰⣾⣾⣾⣾⠟ ⠈⠻⣦ ⠙⣿⣿⣿⣿⣿⣿⣿⣿⣿⣿⣿⡿⠋ ⠹⣿⣿⣿⣿⣿⣿⣿⣿⣿⣿⣿⣿⣿⣿⣿⣿⠟ ║ ║ ╚═══════║ ╚═══════╝ ════════╝ ║ ║ ╚═══════║ ║ ════════╝ ║ │
|
|
15
|
+
│ │ ⠈⠻⣿⣿⣿⣿⣿⣿⣟⠟⠋ ⠙⣿⣿⣿⣿⠋ ║ ║ ║ ║ ║ ╚═╗ ║ ⠏⠙ │ ⣾⣿⣿⣿⣿⣿⣿⣿⣷ ############ ║ ║ ║ ⢀⣰⣾⣾⣾⣾⠟ ⠈⠻⣷⣦⣄ ⣿⣿⣿⣿⣿⣿⣿⣿⣿⣿⣏ ⣹⣿⣿⣿⣿⣿⣿⣿⣿⣿⣿⣿⣿⣿⠋ │
|
|
16
|
+
│ │ ⠈⠻⢿⡿⠋ ⡿⠋⠙⢿ ╚═════╝ ║ ║ ║ ║ ║ ║ ║║ ║║ │ ⠈⠉ ⠉⠁ ╠═════╦═╝ ╔═══════╗ ╔═══════║ ╔══════╣ ⣀⣀⣀⣀⣀⠤⣾⣾⣾⠟ ⠈⠻⣷⣦⣄ ⣸⣿⣿⣿⣿⣿⣿⣿⣿⣿⣿⣷⣆ ⣰⣾⣿⣿⣿⣿⣿⣿⣿⣿⣿⣿⣿⣿⠋ │
|
|
17
|
+
│ └########################################################################################################################################################################┘ ║ ╚═╗ ║ ║ ║ ║ ╔╝ ║ ################################################################################################################################################################################################################################################################################################################ │
|
|
18
|
+
│ ┌########┐ ║ ║ ║ ║ ║ ║ ║ ║ ################################################################################################################################################################################################################################################################################################################## │
|
|
19
|
+
│ │ │ ║ ║ ╚═══════╝ ╚═══════║ ╚═══════╝ # ######### │ ########## ╭▄─▄─▄─▄─▄─▄─▄─▄─▄─▄─▄─▄─▄─▄─▄─▄─▄─▄─▄─▄─▄─▄─▄─▄─▄─▄─▄─▄─▄─▄─▄─▄╮ ╭▄─▄─▄─▄─▄─▄─▄─▄─▄─▄─▄─▄─▄─▄╮ │
|
|
20
|
+
│ │ │ ############ #═══════════#########══════════════════════════════════════════════════════════════════════════════════════════════════════════════════════════════════════════════════════════════════════════════════════════════════════════════════════════════════════════════════════════╡ ### ### ### ├▀─▀─▀─▀─▀─▀─▀─▀─▀─▀─▀─▀─▀─▀─▀─▀─▀─▀─▀─▀─▀─▀─▀─▀─▀─▀─▀─▀─▀─▀─▀─▀┤ ├▀─▀─▀─▀─▀─▀─▀─▀─▀─▀─▀─▀─▀─▀┤ │
|
|
21
|
+
│ ######## ############ │ │ ############ # ######### ⣠⣤⣤⣤⣤⣄ ⣠⣤⣤⣤⣤⣄ ⣠⣤⣤⣤⣤⣄ ⣠⣤⣤⣤⣤⣄ ⣠⣤⣤⣤⣤⣄ ⣠⣤⣤⣤⣤⣄ ⣠⣤⣤⣤⣤⣄ ⣠⣤⣤⣤⣤⣄ ⣠⣤⣤⣤⣤⣄ ⣠⣤⣤⣤⣤⣄ ⣠⣤⣤⣤⣤⣄ ⣠⣤⣤⣤⣤⣄ │ ╭#╯ ╭## ### │ │ │ │ │
|
|
22
|
+
│ ######## ▓░ ############ │ │ ## ## # #########⠀⠀⠀⠀⠀ ⣿⣿⣿⣿⣿⣿ ⣿⣿⣿⣿⣿⣿ ⣿⣿⣿⣿⣿⣿ ⣿⣿⣿⣿⣿⣿ ⣿⣿⣿⣿⣿⣿ ⣿⣿⣿⣿⣿⣿ ⣿⣿⣿⣿⣿⣿ ⣿⣿⣿⣿⣿⣿ ⣿⣿⣿⣿⣿⣿ ⣿⣿⣿⣿⣿⣿ ⣿⣿⣿⣿⣿⣿ ⣿⣿⣿⣿⣿⣿ ⣶⣶⣶⣶⣶⣶⣶⣶⣶ │ ╭##╯ ╭##╯ ### │ ○ ○ ○ ○ ○ ○ ○ ○ ○ │ │ ○ ○ ○ ○ ○ │ │
|
|
23
|
+
│ ### ######## █ ▓░ ################### ############ ## ## ############ │ │ ############ ############ # ######### ⣿⣿⣿⣿⣿⣿ ⣿⣿⣿⣿⣿⣿ ⣿⣿⣿⣿⣿⣿ ⣿⣿⣿⣿⣿⣿ ⣿⣿⣿⣿⣿⣿ ⣿⣿⣿⣿⣿⣿ ⣿⣿⣿⣿⣿⣿ ⣿⣿⣿⣿⣿⣿ ⣿⣿⣿⣿⣿⣿ ⣿⣿⣿⣿⣿⣿ ⣿⣿⣿⣿⣿⣿ ⣿⣿⣿⣿⣿⣿ ######### │ ╰####╯ #### ╭─┴───────────────────────────────────────────────────────────────┤ ├───────────────────────────┴╮ │
|
|
24
|
+
│ ######## ################################ ######################### ############ ############ ############ ####################### │ ◯ │ ############ # ⢿⣿⣿⣿⣿⣿⣿⣿⡿ ⢿⣿⣿⣿⣿⡿ ⢿⣿⣿⣿⣿⡿ ⢿⣿⣿⣿⣿⡿ ⢿⣿⣿⣿⣿⡿ ⢿⣿⣿⣿⣿⡿ ⢿⣿⣿⣿⣿⡿ ⢿⣿⣿⣿⣿⡿ ⢿⣿⣿⣿⣿⡿ ⢿⣿⣿⣿⣿⡿ ⢿⣿⣿⣿⣿⡿ ⢿⣿⣿⣿⣿⡿ ⢿⣿⣿⣿⣿⡿ ######### │ ╭## ### ├╥─╥─╥─╥─╥─╥─╥─╥─╥─╥─╥─╥─╥─╥─╥─╥─╥─╥─╥─╥─╥─╥─╥─╥─╥─╥─╥─╥─╥─╥─╥─╥─╥┴╥─╥─╥─╥─╥─╥┴╥─╥─╥─╥─╥─╥─╥─╥─╥─╥─╥─╥─╥─╥─┤ │
|
|
25
|
+
│ ############################ # # ######################### ############ ## ## ## ## # # │ │ ############ ## ## # ⠀ ######### │ ╭#╯ ### │║ ║ ║ ║ ║ ║ ║ ║ ║ ║ ║ ║ ║ ║ ║ ║ ║ ║ ║ ║ ║ ║ ║ ║ ║ ║ ║ ║ ║ ║ ║ ║ ║ ║ ║ ║ ║ ║ ║ ║ ║ ║ ║ ║ ║ ║ ║ ║ ║ ║ ║ ║ ║ │ │
|
|
26
|
+
│ ############################# # # ######################### ############ ############ ############ # # │ │ ############ ############ # ⠀ ######### │ ╭#╯ # ╭─┴╨─╨─╨─╨─╨─╨─╨─╨─╨─╨─╨─╨─╨─╨─╨─╨─╨─╨─╨─╨─╨─╨─╨─╨─╨─╨─╨─╨─╨─╨─╨─╨─╨─╨─╨─╨─╨─╨─╨─╨─╨─╨─╨─╨─╨─╨─╨─╨─╨─╨─╨─╨─╨─┤ │
|
|
27
|
+
│ ############################# # # ######################### ## ## # # │ │ ## ## # ⠀⠀⠀⠀⠀⠀⠀ ######### │ ╭#╯ # ├─▄─▄┐ ┌▄─▄─▄─▄─▄─▄─▄┐ ┌▄─▄─▄─▄─▄─▄─▄─▄┐ ┌▄─▄─▄─▄─▄─▄─▄┐ ▄▄▄▄▄▄▄#####▄#▄#▄#▄#▄#▄┐ ┌▄#▄#▄#▄#┤ │
|
|
28
|
+
│ ### ### # # ### ### ############ # # │ │ ############ #################################################################################################################################################################################################################################################################⠛⠛⠛⠛⠛⠛⠛⠛⠛#####┴################################┴############### ├──▀─▘ ▝─▀─▀─▀─▀─▀─▀─▘ ▝─▀─▀─▀─▀─▀─▀─▀─▘ ▝─▀─▀─▀─▀─▀─▀─▘ ███████######▀#▀#▀#▀#▀#▘ ▝#▀#▀#▀#▀┤ │
|
|
29
|
+
│ └########┘ ╰────────────────────────────────────────────────────────────────────-▀▀▀▀▀▀▀▀▀##############################╯ │
|
|
30
|
+
└###########################################################################################################################################################################################################################################################################################################################################################################################################################################################################################################################################################################################################################################################################################################################################################################################################################################################################################################################################################################┘
|