beats 2.1.0 → 2.1.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 +5 -5
- data/LICENSE +2 -2
- data/README.markdown +17 -80
- data/bin/beats +2 -7
- data/lib/beats.rb +12 -6
- data/lib/beats/{audioengine.rb → audio_engine.rb} +7 -8
- data/lib/beats/{audioutils.rb → audio_utils.rb} +35 -17
- data/lib/beats/{beatsrunner.rb → beats_runner.rb} +2 -2
- data/lib/beats/kit.rb +6 -5
- data/lib/beats/kit_builder.rb +12 -8
- data/lib/beats/pattern.rb +7 -16
- data/lib/beats/song.rb +7 -8
- data/lib/beats/{songoptimizer.rb → song_optimizer.rb} +11 -8
- data/lib/beats/{songparser.rb → song_parser.rb} +46 -48
- data/lib/beats/track.rb +14 -17
- data/lib/beats/transforms/song_swinger.rb +7 -5
- data/lib/wavefile/{cachingwriter.rb → caching_writer.rb} +2 -2
- data/test/{audioengine_test.rb → audio_engine_test.rb} +49 -46
- data/test/audio_utils_test.rb +86 -0
- data/test/{cachingwriter_test.rb → caching_writer_test.rb} +0 -0
- data/test/fixtures/invalid/sound_in_kit_wrong_format.txt +1 -1
- data/test/fixtures/invalid/sound_in_track_wrong_format.txt +1 -1
- data/test/fixtures/valid/empty_kit.txt +14 -0
- data/test/fixtures/valid/example_song_header_different_capitalization.txt +21 -0
- data/test/fixtures/valid/multiple_patterns_same_name.txt +31 -0
- data/test/fixtures/valid/multiple_song_header_sections.txt +29 -0
- data/test/includes.rb +0 -9
- data/test/kit_builder_test.rb +20 -0
- data/test/kit_test.rb +7 -0
- data/test/pattern_test.rb +86 -74
- data/test/{songoptimizer_test.rb → song_optimizer_test.rb} +5 -8
- data/test/{songparser_test.rb → song_parser_test.rb} +109 -13
- data/test/song_swinger_test.rb +6 -4
- data/test/song_test.rb +32 -14
- data/test/sounds/agogo_high_stereo_16.wav +0 -0
- data/test/sounds/agogo_low_stereo_16.wav +0 -0
- data/test/sounds/bass2_stereo_16.wav +0 -0
- data/test/sounds/bass_stereo_16.wav +0 -0
- data/test/sounds/clave_high_stereo_16.wav +0 -0
- data/test/sounds/clave_low_stereo_16.wav +0 -0
- data/test/sounds/conga_high_stereo_16.wav +0 -0
- data/test/sounds/conga_low_stereo_16.wav +0 -0
- data/test/sounds/cowbell_high_stereo_16.wav +0 -0
- data/test/sounds/cowbell_low_stereo_16.wav +0 -0
- data/test/sounds/hh_closed_stereo_16.wav +0 -0
- data/test/sounds/hh_open_stereo_16.wav +0 -0
- data/test/sounds/ride_stereo_16.wav +0 -0
- data/test/sounds/rim_stereo_16.wav +0 -0
- data/test/sounds/snare2_stereo_16.wav +0 -0
- data/test/sounds/snare_stereo_16.wav +0 -0
- data/test/sounds/tom1_stereo_16.wav +0 -0
- data/test/sounds/tom2_stereo_16.wav +0 -0
- data/test/sounds/tom3_stereo_16.wav +0 -0
- data/test/sounds/tom4_stereo_16.wav +0 -0
- data/test/track_test.rb +51 -5
- metadata +184 -176
- data/test/audioutils_test.rb +0 -46
@@ -50,12 +50,11 @@ Verse:
|
|
50
50
|
- snare: ..........X."
|
51
51
|
|
52
52
|
def self.load_fixture(fixture_name)
|
53
|
-
SongParser.
|
53
|
+
SongParser.parse(FIXTURE_BASE_PATH, File.read("test/fixtures/#{fixture_name}"))
|
54
54
|
end
|
55
55
|
|
56
56
|
def test_optimize
|
57
|
-
|
58
|
-
original_song, kit = parser.parse(File.dirname(__FILE__), EXAMPLE_SONG_YAML)
|
57
|
+
original_song, _ = SongParser.parse(File.dirname(__FILE__), EXAMPLE_SONG_YAML)
|
59
58
|
|
60
59
|
optimizer = SongOptimizer.new
|
61
60
|
optimized_song = optimizer.optimize(original_song, 4)
|
@@ -123,8 +122,7 @@ Verse:
|
|
123
122
|
end
|
124
123
|
|
125
124
|
def test_optimize_song_nondivisible_max_pattern_length
|
126
|
-
|
127
|
-
original_song, kit = parser.parse(File.dirname(__FILE__), EXAMPLE_SONG_YAML_EMPTY_SUB_PATTERN)
|
125
|
+
original_song, _ = SongParser.parse(File.dirname(__FILE__), EXAMPLE_SONG_YAML_EMPTY_SUB_PATTERN)
|
128
126
|
|
129
127
|
optimizer = SongOptimizer.new
|
130
128
|
optimized_song = optimizer.optimize(original_song, 7)
|
@@ -142,7 +140,7 @@ Verse:
|
|
142
140
|
end
|
143
141
|
|
144
142
|
def test_pattern_collision
|
145
|
-
original_song,
|
143
|
+
original_song, _ = SongOptimizerTest.load_fixture("valid/optimize_pattern_collision.txt")
|
146
144
|
optimizer = SongOptimizer.new
|
147
145
|
optimized_song = optimizer.optimize(original_song, 4)
|
148
146
|
|
@@ -150,8 +148,7 @@ Verse:
|
|
150
148
|
end
|
151
149
|
|
152
150
|
def test_optimize_song_containing_empty_pattern
|
153
|
-
|
154
|
-
original_song, kit = parser.parse(File.dirname(__FILE__), EXAMPLE_SONG_YAML_EMPTY_SUB_PATTERN)
|
151
|
+
original_song, _ = SongParser.parse(File.dirname(__FILE__), EXAMPLE_SONG_YAML_EMPTY_SUB_PATTERN)
|
155
152
|
|
156
153
|
optimizer = SongOptimizer.new
|
157
154
|
optimized_song = optimizer.optimize(original_song, 4)
|
@@ -24,24 +24,68 @@ class SongParserTest < Minitest::Test
|
|
24
24
|
:sound_in_kit_wrong_format,
|
25
25
|
:sound_in_track_wrong_format]
|
26
26
|
|
27
|
-
|
27
|
+
def test_song_header_different_capitalization
|
28
|
+
song, kit = load_fixture("valid/example_song_header_different_capitalization.txt")
|
29
|
+
|
30
|
+
assert_equal(100, song.tempo)
|
31
|
+
assert_equal([:verse, :chorus, :chorus, :verse, :chorus, :chorus], song.flow)
|
32
|
+
assert_equal(["bass", "snare", "empty_track_placeholder_name_234hkj32hjk4hjkhds23"], kit.labels)
|
33
|
+
assert_equal(2, song.patterns.length)
|
34
|
+
assert_equal(2, song.patterns[:verse].tracks.length)
|
35
|
+
assert_equal("X...X...X...X...", song.patterns[:verse].tracks["bass"].rhythm)
|
36
|
+
assert_equal("..............X.", song.patterns[:verse].tracks["snare"].rhythm)
|
37
|
+
assert_equal(2, song.patterns[:chorus].tracks.length)
|
38
|
+
assert_equal("X...X...XX..X...", song.patterns[:chorus].tracks["bass"].rhythm)
|
39
|
+
assert_equal("....X.......X...", song.patterns[:chorus].tracks["snare"].rhythm)
|
40
|
+
end
|
41
|
+
|
42
|
+
def test_multiple_song_headers
|
43
|
+
song, kit = load_fixture("valid/multiple_song_header_sections.txt")
|
44
|
+
|
45
|
+
assert_equal(200, song.tempo)
|
46
|
+
assert_equal([:chorus, :chorus, :chorus, :chorus], song.flow)
|
47
|
+
assert_equal(["bass", "snare", "empty_track_placeholder_name_234hkj32hjk4hjkhds23"], kit.labels)
|
48
|
+
assert_equal(2, song.patterns.length)
|
49
|
+
assert_equal(2, song.patterns[:verse].tracks.length)
|
50
|
+
assert_equal("X...X...X...X...", song.patterns[:verse].tracks["bass"].rhythm)
|
51
|
+
assert_equal("..............X.", song.patterns[:verse].tracks["snare"].rhythm)
|
52
|
+
assert_equal(2, song.patterns[:chorus].tracks.length)
|
53
|
+
assert_equal("X...X...XX..X...", song.patterns[:chorus].tracks["bass"].rhythm)
|
54
|
+
assert_equal("....X.......X...", song.patterns[:chorus].tracks["snare"].rhythm)
|
55
|
+
end
|
56
|
+
|
57
|
+
def test_multiple_patterns_same_name
|
58
|
+
song, kit = load_fixture("valid/multiple_patterns_same_name.txt")
|
59
|
+
|
60
|
+
assert_equal(120, song.tempo)
|
61
|
+
assert_equal([:verse, :verse, :chorus, :chorus, :verse, :verse, :chorus, :chorus], song.flow)
|
62
|
+
assert_equal(["bass", "snare", "hh_closed", "agogo", "test/sounds/tom4_mono_8.wav", "empty_track_placeholder_name_234hkj32hjk4hjkhds23"], kit.labels)
|
63
|
+
assert_equal(2, song.patterns.length)
|
64
|
+
assert_equal(3, song.patterns[:verse].tracks.length)
|
65
|
+
assert_equal("X.X.X.X.", song.patterns[:verse].tracks["bass"].rhythm)
|
66
|
+
assert_equal(".X.X.X.X", song.patterns[:verse].tracks["snare"].rhythm)
|
67
|
+
assert_equal("XXXXXX..", song.patterns[:verse].tracks["test/sounds/tom4_mono_8.wav"].rhythm)
|
68
|
+
assert_equal(2, song.patterns[:chorus].tracks.length)
|
69
|
+
assert_equal("X...X...XX..X...", song.patterns[:chorus].tracks["bass"].rhythm)
|
70
|
+
assert_equal("....X.......X...", song.patterns[:chorus].tracks["snare"].rhythm)
|
71
|
+
end
|
28
72
|
|
29
73
|
def test_no_tempo
|
30
|
-
song,
|
74
|
+
song, _ = load_fixture("valid/no_tempo.txt")
|
31
75
|
|
32
76
|
assert_equal(120, song.tempo)
|
33
77
|
assert_equal([:verse], song.flow)
|
34
78
|
end
|
35
79
|
|
36
80
|
def test_fractional_tempo
|
37
|
-
song,
|
81
|
+
song, _ = load_fixture("valid/fractional_tempo.txt")
|
38
82
|
|
39
83
|
assert_equal(95.764, song.tempo)
|
40
84
|
assert_equal([:verse, :verse, :chorus, :chorus], song.flow)
|
41
85
|
end
|
42
86
|
|
43
87
|
def test_repeats_not_specified
|
44
|
-
song,
|
88
|
+
song, _ = load_fixture("valid/repeats_not_specified.txt")
|
45
89
|
|
46
90
|
assert_equal(100, song.tempo)
|
47
91
|
assert_equal([:verse], song.flow)
|
@@ -51,6 +95,7 @@ class SongParserTest < Minitest::Test
|
|
51
95
|
song, kit = load_fixture("valid/example_flow_patterns_different_capitalization.txt")
|
52
96
|
|
53
97
|
assert_equal(100, song.tempo)
|
98
|
+
assert_equal(["bass", "snare", "empty_track_placeholder_name_234hkj32hjk4hjkhds23"], kit.labels)
|
54
99
|
assert_equal([:verse, :chorus, :chorus, :verse, :chorus, :chorus], song.flow)
|
55
100
|
assert_equal(2, song.patterns.length)
|
56
101
|
assert_equal(2, song.patterns[:verse].tracks.length)
|
@@ -61,10 +106,39 @@ class SongParserTest < Minitest::Test
|
|
61
106
|
assert_equal("....X.......X...", song.patterns[:chorus].tracks["snare"].rhythm)
|
62
107
|
end
|
63
108
|
|
109
|
+
def test_song_with_empty_kit
|
110
|
+
song, kit = load_fixture("valid/empty_kit.txt")
|
111
|
+
|
112
|
+
assert_equal(100, song.tempo)
|
113
|
+
assert_equal(["test/sounds/bass_mono_8.wav", "test/sounds/snare_mono_8.wav", "empty_track_placeholder_name_234hkj32hjk4hjkhds23"], kit.labels)
|
114
|
+
assert_equal([:verse, :verse, :chorus, :chorus], song.flow)
|
115
|
+
assert_equal(2, song.patterns.length)
|
116
|
+
assert_equal(2, song.patterns[:verse].tracks.length)
|
117
|
+
assert_equal("X...X...", song.patterns[:verse].tracks["test/sounds/bass_mono_8.wav"].rhythm)
|
118
|
+
assert_equal("..X...X.", song.patterns[:verse].tracks["test/sounds/snare_mono_8.wav"].rhythm)
|
119
|
+
assert_equal(2, song.patterns[:chorus].tracks.length)
|
120
|
+
assert_equal("XXXXXXXX", song.patterns[:chorus].tracks["test/sounds/bass_mono_8.wav"].rhythm)
|
121
|
+
assert_equal(".X.X.X.X", song.patterns[:chorus].tracks["test/sounds/snare_mono_8.wav"].rhythm)
|
122
|
+
end
|
123
|
+
|
64
124
|
def test_song_with_unused_kit
|
65
125
|
no_kit_song, no_kit_kit = load_fixture("valid/example_no_kit.txt")
|
66
126
|
kit_song, kit_kit = load_fixture("valid/example_with_kit.txt")
|
67
127
|
|
128
|
+
assert_equal(["test/sounds/bass_mono_8.wav",
|
129
|
+
"test/sounds/snare_mono_8.wav",
|
130
|
+
"test/sounds/hh_closed_mono_8.wav",
|
131
|
+
"test/sounds/hh_open_mono_8.wav",
|
132
|
+
"test/sounds/ride_mono_8.wav",
|
133
|
+
"empty_track_placeholder_name_234hkj32hjk4hjkhds23"], no_kit_kit.labels)
|
134
|
+
assert_equal(["bass",
|
135
|
+
"snare",
|
136
|
+
"hhclosed",
|
137
|
+
"hhopen",
|
138
|
+
"test/sounds/hh_closed_mono_8.wav",
|
139
|
+
"test/sounds/ride_mono_8.wav",
|
140
|
+
"empty_track_placeholder_name_234hkj32hjk4hjkhds23"], kit_kit.labels)
|
141
|
+
|
68
142
|
# These two songs should be the same, except that one uses a kit in the song header
|
69
143
|
# and the other doesn't.
|
70
144
|
[no_kit_song, kit_song].each do |song|
|
@@ -84,7 +158,7 @@ class SongParserTest < Minitest::Test
|
|
84
158
|
end
|
85
159
|
|
86
160
|
def test_empty_track
|
87
|
-
song,
|
161
|
+
song, _ = load_fixture("valid/example_with_empty_track.txt")
|
88
162
|
|
89
163
|
assert_equal(1, song.patterns.length)
|
90
164
|
assert_equal(2, song.patterns[:verse].tracks.length)
|
@@ -93,7 +167,7 @@ class SongParserTest < Minitest::Test
|
|
93
167
|
end
|
94
168
|
|
95
169
|
def test_track_with_spaces
|
96
|
-
song,
|
170
|
+
song, _ = load_fixture("valid/track_with_spaces.txt")
|
97
171
|
|
98
172
|
assert_equal(1, song.patterns.length)
|
99
173
|
assert_equal(2, song.patterns[:verse].tracks.length)
|
@@ -102,7 +176,7 @@ class SongParserTest < Minitest::Test
|
|
102
176
|
end
|
103
177
|
|
104
178
|
def test_multiple_tracks_same_sound
|
105
|
-
song,
|
179
|
+
song, _ = load_fixture("valid/multiple_tracks_same_sound.txt")
|
106
180
|
|
107
181
|
assert_equal(2, song.patterns.length)
|
108
182
|
assert_equal(7, song.patterns[:verse].tracks.length)
|
@@ -126,7 +200,7 @@ class SongParserTest < Minitest::Test
|
|
126
200
|
end
|
127
201
|
|
128
202
|
def test_swung_8
|
129
|
-
song,
|
203
|
+
song, _ = load_fixture("valid/example_swung_8th.txt")
|
130
204
|
|
131
205
|
assert_equal(180, song.tempo)
|
132
206
|
assert_equal([:verse, :verse, :chorus, :chorus], song.flow)
|
@@ -140,7 +214,7 @@ class SongParserTest < Minitest::Test
|
|
140
214
|
end
|
141
215
|
|
142
216
|
def test_swung_16
|
143
|
-
song,
|
217
|
+
song, _ = load_fixture("valid/example_swung_16th.txt")
|
144
218
|
|
145
219
|
assert_equal(180, song.tempo)
|
146
220
|
assert_equal([:verse, :verse, :chorus, :chorus], song.flow)
|
@@ -154,7 +228,7 @@ class SongParserTest < Minitest::Test
|
|
154
228
|
end
|
155
229
|
|
156
230
|
def test_unswung_song
|
157
|
-
song,
|
231
|
+
song, _ = load_fixture("valid/example_unswung.txt")
|
158
232
|
|
159
233
|
assert_equal(120, song.tempo)
|
160
234
|
assert_equal([:verse, :verse, :chorus, :chorus], song.flow)
|
@@ -171,6 +245,7 @@ class SongParserTest < Minitest::Test
|
|
171
245
|
song, kit = load_fixture("valid/track_with_composite_kit_sounds.txt")
|
172
246
|
|
173
247
|
assert_equal(100, song.tempo)
|
248
|
+
assert_equal(["bass", "snare", "hh_closed", "empty_track_placeholder_name_234hkj32hjk4hjkhds23"], kit.labels)
|
174
249
|
assert_equal([:verse, :verse, :chorus, :chorus], song.flow)
|
175
250
|
assert_equal(2, song.patterns.length)
|
176
251
|
assert_equal(3, song.patterns[:verse].tracks.length)
|
@@ -187,6 +262,12 @@ class SongParserTest < Minitest::Test
|
|
187
262
|
song, kit = load_fixture("valid/track_with_composite_non_kit_sound.txt")
|
188
263
|
|
189
264
|
assert_equal(100, song.tempo)
|
265
|
+
assert_equal(["bass",
|
266
|
+
"snare",
|
267
|
+
"hh_closed",
|
268
|
+
"test/sounds/agogo_high_mono_8.wav",
|
269
|
+
"test/sounds/hh_open_mono_8.wav",
|
270
|
+
"empty_track_placeholder_name_234hkj32hjk4hjkhds23"], kit.labels)
|
190
271
|
assert_equal([:verse, :verse, :chorus, :chorus], song.flow)
|
191
272
|
assert_equal(2, song.patterns.length)
|
192
273
|
assert_equal(2, song.patterns[:verse].tracks.length)
|
@@ -202,6 +283,11 @@ class SongParserTest < Minitest::Test
|
|
202
283
|
song, kit = load_fixture("valid/track_with_composite_mix_kit_and_not_kit_sound.txt")
|
203
284
|
|
204
285
|
assert_equal(100, song.tempo)
|
286
|
+
assert_equal(["bass",
|
287
|
+
"snare",
|
288
|
+
"hh_closed",
|
289
|
+
"test/sounds/hh_open_mono_8.wav",
|
290
|
+
"empty_track_placeholder_name_234hkj32hjk4hjkhds23"], kit.labels)
|
205
291
|
assert_equal([:verse, :verse, :chorus, :chorus], song.flow)
|
206
292
|
assert_equal(2, song.patterns.length)
|
207
293
|
assert_equal(2, song.patterns[:verse].tracks.length)
|
@@ -217,6 +303,13 @@ class SongParserTest < Minitest::Test
|
|
217
303
|
song, kit = load_fixture("valid/track_with_composite_mix_kit_and_not_kit_sound_2.txt")
|
218
304
|
|
219
305
|
assert_equal(100, song.tempo)
|
306
|
+
assert_equal(["bass",
|
307
|
+
"snare",
|
308
|
+
"hihat-hh_closed_mono_8",
|
309
|
+
"hihat-hh_open_mono_8",
|
310
|
+
"test/sounds/agogo_high_mono_8.wav",
|
311
|
+
"test/sounds/agogo_low_mono_8.wav",
|
312
|
+
"empty_track_placeholder_name_234hkj32hjk4hjkhds23"], kit.labels)
|
220
313
|
assert_equal([:verse, :verse, :chorus, :chorus], song.flow)
|
221
314
|
assert_equal(2, song.patterns.length)
|
222
315
|
assert_equal(3, song.patterns[:verse].tracks.length)
|
@@ -235,6 +328,7 @@ class SongParserTest < Minitest::Test
|
|
235
328
|
song, kit = load_fixture("valid/track_with_composite_single_sound.txt")
|
236
329
|
|
237
330
|
assert_equal(100, song.tempo)
|
331
|
+
assert_equal(["bass", "snare", "hh_closed", "empty_track_placeholder_name_234hkj32hjk4hjkhds23"], kit.labels)
|
238
332
|
assert_equal([:verse, :verse, :chorus, :chorus], song.flow)
|
239
333
|
assert_equal(2, song.patterns.length)
|
240
334
|
assert_equal(2, song.patterns[:verse].tracks.length)
|
@@ -249,6 +343,7 @@ class SongParserTest < Minitest::Test
|
|
249
343
|
song, kit = load_fixture("valid/kit_with_composite_sounds.txt")
|
250
344
|
|
251
345
|
assert_equal(100, song.tempo)
|
346
|
+
assert_equal(["bass", "snare", "hihat-hh_closed_mono_8", "hihat-hh_open_mono_8", "empty_track_placeholder_name_234hkj32hjk4hjkhds23"], kit.labels)
|
252
347
|
assert_equal([:verse, :verse, :chorus, :chorus], song.flow)
|
253
348
|
assert_equal(2, song.patterns.length)
|
254
349
|
assert_equal(3, song.patterns[:verse].tracks.length)
|
@@ -266,6 +361,7 @@ class SongParserTest < Minitest::Test
|
|
266
361
|
song, kit = load_fixture("valid/kit_with_composite_single_sound.txt")
|
267
362
|
|
268
363
|
assert_equal(100, song.tempo)
|
364
|
+
assert_equal(["bass", "snare", "hihat-hh_closed_mono_8", "empty_track_placeholder_name_234hkj32hjk4hjkhds23"], kit.labels)
|
269
365
|
assert_equal([:verse, :verse, :chorus, :chorus], song.flow)
|
270
366
|
assert_equal(2, song.patterns.length)
|
271
367
|
assert_equal(2, song.patterns[:verse].tracks.length)
|
@@ -280,18 +376,18 @@ class SongParserTest < Minitest::Test
|
|
280
376
|
def test_invalid_parse
|
281
377
|
INVALID_FIXTURES.each do |fixture|
|
282
378
|
assert_raises(SongParser::ParseError) do
|
283
|
-
|
379
|
+
_, _ = load_fixture("invalid/#{fixture}.txt")
|
284
380
|
end
|
285
381
|
end
|
286
382
|
|
287
383
|
assert_raises(Track::InvalidRhythmError) do
|
288
|
-
|
384
|
+
_, _ = load_fixture("invalid/bad_rhythm.txt")
|
289
385
|
end
|
290
386
|
end
|
291
387
|
|
292
388
|
private
|
293
389
|
|
294
390
|
def load_fixture(fixture_name)
|
295
|
-
SongParser.
|
391
|
+
SongParser.parse(FIXTURE_BASE_PATH, File.read("test/fixtures/#{fixture_name}"))
|
296
392
|
end
|
297
393
|
end
|
data/test/song_swinger_test.rb
CHANGED
@@ -3,7 +3,7 @@ require 'includes'
|
|
3
3
|
class SongSwingerTest < Minitest::Test
|
4
4
|
def test_full_song_swing_rate_8
|
5
5
|
base_path = File.dirname(__FILE__) + "/sounds"
|
6
|
-
song,
|
6
|
+
song, _ = SongParser.parse(base_path, File.read("test/fixtures/valid/example_mono_16_base_path.txt"))
|
7
7
|
|
8
8
|
shuffled_song = Transforms::SongSwinger.transform(song, 8)
|
9
9
|
|
@@ -47,7 +47,7 @@ class SongSwingerTest < Minitest::Test
|
|
47
47
|
|
48
48
|
def test_full_song_swing_rate_16
|
49
49
|
base_path = File.dirname(__FILE__) + "/sounds"
|
50
|
-
song,
|
50
|
+
song, _ = SongParser.parse(base_path, File.read("test/fixtures/valid/example_mono_16_base_path.txt"))
|
51
51
|
|
52
52
|
shuffled_song = Transforms::SongSwinger.transform(song, 16)
|
53
53
|
|
@@ -157,8 +157,10 @@ class SongSwingerTest < Minitest::Test
|
|
157
157
|
expectations.each do |original_rhythm, expected_rhythm|
|
158
158
|
song = Song.new
|
159
159
|
|
160
|
-
|
161
|
-
|
160
|
+
pattern_tracks = [
|
161
|
+
Track.new("track1", original_rhythm),
|
162
|
+
]
|
163
|
+
pattern = song.pattern(:my_pattern, pattern_tracks)
|
162
164
|
|
163
165
|
song.pattern(pattern)
|
164
166
|
|
data/test/song_test.rb
CHANGED
@@ -13,25 +13,30 @@ class SongTest < Minitest::Test
|
|
13
13
|
test_songs[:blank] = Song.new
|
14
14
|
|
15
15
|
test_songs[:no_flow] = Song.new
|
16
|
-
|
17
|
-
|
18
|
-
|
19
|
-
|
16
|
+
verse_tracks = [
|
17
|
+
Track.new("bass.wav", "X.......X......."),
|
18
|
+
Track.new("snare.wav", "....X.......X..."),
|
19
|
+
Track.new("hh_closed.wav", "X.X.X.X.X.X.X.X."),
|
20
|
+
]
|
21
|
+
test_songs[:no_flow].pattern(:verse, verse_tracks)
|
20
22
|
|
21
|
-
song_parser = SongParser.new
|
22
23
|
FIXTURES.each do |fixture_name|
|
23
|
-
test_songs[fixture_name],
|
24
|
+
test_songs[fixture_name], _ = SongParser.parse(base_path, File.read("test/fixtures/valid/#{fixture_name}.txt"))
|
24
25
|
end
|
25
26
|
|
26
27
|
test_songs[:from_code] = Song.new
|
27
|
-
|
28
|
-
|
29
|
-
|
30
|
-
|
31
|
-
|
32
|
-
|
33
|
-
|
34
|
-
|
28
|
+
verse_tracks = [
|
29
|
+
Track.new("bass.wav", "X.......X......."),
|
30
|
+
Track.new("snare.wav", "....X.......X..."),
|
31
|
+
Track.new("hh_closed.wav", "X.X.X.X.X.X.X.X."),
|
32
|
+
]
|
33
|
+
test_songs[:from_code].pattern(:verse, verse_tracks)
|
34
|
+
chorus_tracks = [
|
35
|
+
Track.new("bass.wav", "X......."),
|
36
|
+
Track.new("snare.wav", "....X..X"),
|
37
|
+
Track.new("ride.wav", "X.....X."),
|
38
|
+
]
|
39
|
+
test_songs[:from_code].pattern(:chorus, chorus_tracks)
|
35
40
|
test_songs[:from_code].flow = [:verse, :chorus, :verse, :chorus, :chorus]
|
36
41
|
|
37
42
|
test_songs
|
@@ -74,6 +79,19 @@ class SongTest < Minitest::Test
|
|
74
79
|
chorus = song.pattern(:Chorus)
|
75
80
|
assert_equal(2, song.patterns.length)
|
76
81
|
assert_equal({:Chorus => chorus, :Verse => verse2}, song.patterns)
|
82
|
+
|
83
|
+
tracks = [
|
84
|
+
Track.new("track1", "X...X..."),
|
85
|
+
Track.new("track2", "X..."),
|
86
|
+
]
|
87
|
+
tracks_provided = song.pattern(:Tracks_Provided, tracks)
|
88
|
+
assert_equal(3, song.patterns.length)
|
89
|
+
assert_equal({:Chorus => chorus, :Tracks_Provided => tracks_provided, :Verse => verse2}, song.patterns)
|
90
|
+
assert_equal(["track1", "track2"], song.track_names)
|
91
|
+
assert_equal(tracks_provided.tracks["track1"].rhythm, "X...X...")
|
92
|
+
assert_equal(tracks_provided.tracks["track1"].name, "track1")
|
93
|
+
assert_equal(tracks_provided.tracks["track2"].rhythm, "X.......")
|
94
|
+
assert_equal(tracks_provided.tracks["track2"].name, "track2")
|
77
95
|
end
|
78
96
|
|
79
97
|
def test_total_tracks
|
Binary file
|
Binary file
|
Binary file
|
Binary file
|
Binary file
|
Binary file
|
Binary file
|
Binary file
|
Binary file
|
Binary file
|
Binary file
|
Binary file
|
Binary file
|
Binary file
|
Binary file
|
Binary file
|
Binary file
|
Binary file
|
Binary file
|
Binary file
|
data/test/track_test.rb
CHANGED
@@ -44,13 +44,59 @@ class TrackTest < Minitest::Test
|
|
44
44
|
assert_equal("..XX..X...X...X.X...X...X...X...", test_tracks[:complicated].rhythm)
|
45
45
|
end
|
46
46
|
|
47
|
+
def test_invalid_name
|
48
|
+
assert_raises(ArgumentError) { Track.new(:verse, "X...X...|X...X...") }
|
49
|
+
assert_raises(ArgumentError) { Track.new([], "X...X...|X...X...") }
|
50
|
+
assert_raises(ArgumentError) { Track.new({ :foo => :bar }, "X...X...|X...X...") }
|
51
|
+
end
|
52
|
+
|
53
|
+
def test_name_is_frozen
|
54
|
+
original_name = "Verse"
|
55
|
+
track = Track.new(original_name, "X...X...|X...X...")
|
56
|
+
|
57
|
+
# Track is initialized properly
|
58
|
+
assert_equal("Verse", track.name)
|
59
|
+
assert_equal("Verse", original_name)
|
60
|
+
|
61
|
+
# Name is frozen
|
62
|
+
assert_raises(RuntimeError) { track.name << "X" }
|
63
|
+
|
64
|
+
# Changing the original string doesn't modify the track name
|
65
|
+
original_name << "2"
|
66
|
+
assert_equal("Verse", track.name)
|
67
|
+
assert_equal("Verse2", original_name)
|
68
|
+
end
|
69
|
+
|
70
|
+
def test_rhythm_is_frozen
|
71
|
+
original_rhythm = "X...X...|X...X..."
|
72
|
+
track = Track.new("my_track", original_rhythm)
|
73
|
+
|
74
|
+
# Track is initialized properly
|
75
|
+
assert_equal("X...X...X...X...", track.rhythm)
|
76
|
+
assert_equal("X...X...|X...X...", original_rhythm)
|
77
|
+
|
78
|
+
# Rhythm is frozen
|
79
|
+
assert_raises(RuntimeError) { track.rhythm << "X" }
|
80
|
+
|
81
|
+
# Changing the original string doesn't modify the rhythm
|
82
|
+
original_rhythm << "X"
|
83
|
+
assert_equal("X...X...X...X...", track.rhythm)
|
84
|
+
assert_equal("X...X...|X...X...X", original_rhythm)
|
85
|
+
end
|
86
|
+
|
47
87
|
def test_invalid_rhythm
|
48
|
-
|
49
|
-
|
88
|
+
[nil, 12, [], {}, :"X...X...", "abcde", "X.X.e.X"].each do |bad_rhythm|
|
89
|
+
assert_raises(Track::InvalidRhythmError) { Track.new("bad_rhythm", bad_rhythm) }
|
90
|
+
end
|
91
|
+
end
|
92
|
+
|
93
|
+
def test_trigger_step_lengths_is_frozen
|
94
|
+
track = Track.new("my_track", "X...X...|X...X...")
|
95
|
+
|
96
|
+
assert_equal([0, 4, 4, 4, 4], track.trigger_step_lengths)
|
50
97
|
|
51
|
-
track =
|
52
|
-
assert_raises(
|
53
|
-
assert_raises(Track::InvalidRhythmError) { track.rhythm = "X.X.e.X" }
|
98
|
+
assert_raises(RuntimeError) { track.trigger_step_lengths[2] = 5 }
|
99
|
+
assert_raises(RuntimeError) { track.trigger_step_lengths << [1] }
|
54
100
|
end
|
55
101
|
|
56
102
|
def test_step_count
|