musicality 0.8.0 → 0.9.0
Sign up to get free protection for your applications and to get access to all the features.
- checksums.yaml +4 -4
- data/ChangeLog.md +27 -1
- data/README.md +153 -10
- data/bin/collidify +102 -0
- data/bin/lilify +57 -29
- data/bin/midify +64 -24
- data/bin/musicality +39 -0
- data/examples/composition/auto_counterpoint.rb +4 -5
- data/examples/composition/part_generator.rb +8 -2
- data/examples/composition/scale_exercise.rb +1 -1
- data/examples/notation/notes.rb +27 -0
- data/examples/notation/parts.rb +51 -0
- data/examples/notation/scores.rb +38 -0
- data/examples/notation/twinkle.rb +34 -0
- data/examples/notation/twinkle.score +33 -0
- data/lib/musicality.rb +46 -11
- data/lib/musicality/composition/dsl/score_dsl.rb +2 -2
- data/lib/musicality/composition/dsl/score_methods.rb +10 -7
- data/lib/musicality/notation/conversion/change_conversion.rb +1 -1
- data/lib/musicality/notation/conversion/note_time_converter.rb +6 -23
- data/lib/musicality/notation/conversion/score_conversion.rb +15 -15
- data/lib/musicality/notation/conversion/score_converter.rb +50 -67
- data/lib/musicality/notation/model/articulations.rb +3 -2
- data/lib/musicality/notation/model/change.rb +15 -6
- data/lib/musicality/notation/model/dynamics.rb +11 -8
- data/lib/musicality/notation/model/instrument.rb +61 -0
- data/lib/musicality/notation/model/instruments.rb +111 -0
- data/lib/musicality/notation/model/key.rb +137 -0
- data/lib/musicality/notation/model/keys.rb +37 -0
- data/lib/musicality/notation/model/link.rb +6 -19
- data/lib/musicality/notation/model/mark.rb +43 -0
- data/lib/musicality/notation/model/marks.rb +11 -0
- data/lib/musicality/notation/model/meter.rb +4 -0
- data/lib/musicality/notation/model/note.rb +42 -28
- data/lib/musicality/notation/model/part.rb +18 -5
- data/lib/musicality/notation/model/pitch.rb +13 -4
- data/lib/musicality/notation/model/score.rb +104 -66
- data/lib/musicality/notation/model/symbols.rb +16 -11
- data/lib/musicality/notation/parsing/articulation_parsing.rb +38 -38
- data/lib/musicality/notation/parsing/articulation_parsing.treetop +14 -14
- data/lib/musicality/notation/parsing/link_parsing.rb +6 -6
- data/lib/musicality/notation/parsing/link_parsing.treetop +3 -3
- data/lib/musicality/notation/parsing/mark_parsing.rb +138 -0
- data/lib/musicality/notation/parsing/mark_parsing.treetop +31 -0
- data/lib/musicality/notation/parsing/note_node.rb +19 -12
- data/lib/musicality/notation/parsing/note_parsing.rb +218 -87
- data/lib/musicality/notation/parsing/note_parsing.treetop +9 -5
- data/lib/musicality/notation/parsing/numbers/nonnegative_integer_parsing.rb +7 -2
- data/lib/musicality/notation/parsing/numbers/nonnegative_integer_parsing.treetop +1 -1
- data/lib/musicality/notation/parsing/numbers/positive_integer_parsing.rb +6 -4
- data/lib/musicality/notation/parsing/numbers/positive_integer_parsing.treetop +1 -1
- data/lib/musicality/notation/util/function.rb +41 -18
- data/lib/musicality/packable.rb +156 -0
- data/lib/musicality/performance/conversion/glissando_converter.rb +2 -2
- data/lib/musicality/performance/conversion/note_sequence_extractor.rb +223 -70
- data/lib/musicality/performance/conversion/portamento_converter.rb +5 -2
- data/lib/musicality/performance/conversion/score_collator.rb +70 -64
- data/lib/musicality/performance/midi/midi_events.rb +3 -3
- data/lib/musicality/performance/midi/midi_settings.rb +127 -0
- data/lib/musicality/performance/midi/midi_util.rb +8 -2
- data/lib/musicality/performance/midi/part_sequencer.rb +19 -18
- data/lib/musicality/performance/midi/score_sequencer.rb +13 -9
- data/lib/musicality/performance/midi/score_sequencing.rb +5 -5
- data/lib/musicality/performance/model/attack.rb +8 -0
- data/lib/musicality/performance/model/duration_functions.rb +23 -0
- data/lib/musicality/performance/model/note_sequence.rb +52 -95
- data/lib/musicality/performance/model/separation.rb +10 -0
- data/lib/musicality/performance/supercollider/add_actions.rb +13 -0
- data/lib/musicality/performance/supercollider/bundle.rb +18 -0
- data/lib/musicality/performance/supercollider/conductor.rb +125 -0
- data/lib/musicality/performance/supercollider/group.rb +71 -0
- data/lib/musicality/performance/supercollider/message.rb +26 -0
- data/lib/musicality/performance/supercollider/node.rb +122 -0
- data/lib/musicality/performance/supercollider/performer.rb +123 -0
- data/lib/musicality/performance/supercollider/score_conducting.rb +17 -0
- data/lib/musicality/performance/supercollider/server.rb +8 -0
- data/lib/musicality/performance/supercollider/synth.rb +43 -0
- data/lib/musicality/performance/supercollider/synthdef.rb +57 -0
- data/lib/musicality/performance/supercollider/synthdef_settings.rb +23 -0
- data/lib/musicality/performance/supercollider/synthdefs.rb +1654 -0
- data/lib/musicality/{composition/model/pitch_class.rb → pitch_class.rb} +1 -1
- data/lib/musicality/{composition/model/pitch_classes.rb → pitch_classes.rb} +9 -9
- data/lib/musicality/printing/lilypond/clef.rb +12 -0
- data/lib/musicality/printing/lilypond/key_engraving.rb +9 -0
- data/lib/musicality/printing/lilypond/lilypond_settings.rb +105 -0
- data/lib/musicality/printing/lilypond/meter_engraving.rb +1 -1
- data/lib/musicality/printing/lilypond/note_engraving.rb +112 -30
- data/lib/musicality/printing/lilypond/part_engraver.rb +114 -3
- data/lib/musicality/printing/lilypond/pitch_class_engraving.rb +22 -0
- data/lib/musicality/printing/lilypond/pitch_engraving.rb +2 -15
- data/lib/musicality/printing/lilypond/score_engraver.rb +44 -73
- data/lib/musicality/printing/lilypond/score_engraving.rb +3 -3
- data/lib/musicality/project/create_tasks.rb +31 -0
- data/lib/musicality/project/file_cleaner.rb +19 -0
- data/lib/musicality/project/file_raker.rb +107 -0
- data/lib/musicality/project/load_config.rb +43 -0
- data/lib/musicality/project/project.rb +64 -0
- data/lib/musicality/version.rb +1 -1
- data/musicality.gemspec +3 -0
- data/spec/composition/util/random_sampler_spec.rb +1 -1
- data/spec/notation/conversion/measure_note_map_spec.rb +1 -1
- data/spec/notation/conversion/note_time_converter_spec.rb +5 -85
- data/spec/notation/conversion/score_conversion_spec.rb +6 -41
- data/spec/notation/conversion/score_converter_spec.rb +19 -137
- data/spec/notation/model/change_spec.rb +55 -0
- data/spec/notation/model/key_spec.rb +171 -0
- data/spec/notation/model/link_spec.rb +34 -5
- data/spec/notation/model/meter_spec.rb +15 -0
- data/spec/notation/model/note_spec.rb +33 -27
- data/spec/notation/model/part_spec.rb +53 -4
- data/spec/notation/model/pitch_spec.rb +15 -0
- data/spec/notation/model/score_spec.rb +64 -72
- data/spec/notation/parsing/link_nodes_spec.rb +3 -3
- data/spec/notation/parsing/link_parsing_spec.rb +6 -6
- data/spec/notation/parsing/note_node_spec.rb +34 -9
- data/spec/notation/parsing/note_parsing_spec.rb +11 -9
- data/spec/notation/parsing/numbers/nonnegative_integer_spec.rb +4 -0
- data/spec/notation/parsing/pitch_node_spec.rb +0 -1
- data/spec/notation/util/value_computer_spec.rb +2 -2
- data/spec/performance/conversion/glissando_converter_spec.rb +9 -9
- data/spec/performance/conversion/note_sequence_extractor_spec.rb +48 -53
- data/spec/performance/conversion/portamento_converter_spec.rb +11 -9
- data/spec/performance/conversion/score_collator_spec.rb +59 -63
- data/spec/performance/midi/midi_util_spec.rb +22 -8
- data/spec/performance/midi/part_sequencer_spec.rb +2 -2
- data/spec/performance/midi/score_sequencer_spec.rb +12 -10
- data/spec/performance/midi/score_sequencing_spec.rb +2 -2
- data/spec/performance/model/note_sequence_spec.rb +41 -134
- data/spec/printing/note_engraving_spec.rb +204 -0
- data/spec/printing/score_engraver_spec.rb +40 -0
- data/spec/spec_helper.rb +1 -0
- metadata +69 -23
- data/examples/notation/hip.rb +0 -32
- data/examples/notation/missed_connection.rb +0 -26
- data/examples/notation/song1.rb +0 -33
- data/examples/notation/song2.rb +0 -32
- data/lib/musicality/notation/model/links.rb +0 -11
- data/lib/musicality/notation/packing/change_packing.rb +0 -56
- data/lib/musicality/notation/packing/part_packing.rb +0 -31
- data/lib/musicality/notation/packing/score_packing.rb +0 -123
- data/lib/musicality/performance/model/note_attacks.rb +0 -19
- data/lib/musicality/performance/util/note_linker.rb +0 -28
- data/spec/notation/packing/change_packing_spec.rb +0 -304
- data/spec/notation/packing/part_packing_spec.rb +0 -66
- data/spec/notation/packing/score_packing_spec.rb +0 -255
- data/spec/performance/util/note_linker_spec.rb +0 -68
data/lib/musicality/version.rb
CHANGED
data/musicality.gemspec
CHANGED
@@ -28,7 +28,7 @@ describe RandomSampler do
|
|
28
28
|
sampler.values.each_with_index do |val,i|
|
29
29
|
count = counts[val]
|
30
30
|
tgt_prob = sampler.probabilities[i]
|
31
|
-
(count / 1000.to_f).should be_within(0.
|
31
|
+
(count / 1000.to_f).should be_within(0.1).of(tgt_prob)
|
32
32
|
end
|
33
33
|
end
|
34
34
|
end
|
@@ -35,7 +35,7 @@ describe 'Conversion.measure_note_map' do
|
|
35
35
|
@first_mc_off = 3
|
36
36
|
@start_meter = THREE_FOUR
|
37
37
|
@new_meter = TWO_FOUR
|
38
|
-
@score = Score::
|
38
|
+
@score = Score::Tempo.new(@start_meter, 120,
|
39
39
|
meter_changes: { @first_mc_off => Change::Immediate.new(@new_meter) },
|
40
40
|
tempo_changes: {
|
41
41
|
"1/2".to_r => Change::Gradual.linear(100,1),
|
@@ -1,92 +1,12 @@
|
|
1
1
|
require File.expand_path(File.dirname(__FILE__) + '/../../spec_helper')
|
2
2
|
|
3
|
-
describe NoteTimeConverter::
|
4
|
-
describe '#notes_per_second_at' do
|
5
|
-
it 'should convert tempo using Tempo::QNPM.to_nps' do
|
6
|
-
tc = ValueComputer.new(
|
7
|
-
120, 1 => Change::Gradual.linear(100,1), 2 => Change::Gradual.linear(150,1))
|
8
|
-
converter = NoteTimeConverter::Unmeasured.new(tc,200)
|
9
|
-
(0..2).step(0.2).each do |offset|
|
10
|
-
nps = Tempo::QNPM.to_nps(tc.at(offset))
|
11
|
-
converter.notes_per_second_at(offset).should eq(nps)
|
12
|
-
end
|
13
|
-
end
|
14
|
-
end
|
15
|
-
|
16
|
-
describe "#time_elapsed" do
|
17
|
-
context "constant tempo" do
|
18
|
-
before :each do
|
19
|
-
@tempo_computer = ValueComputer.new 120
|
20
|
-
sample_rate = 48
|
21
|
-
@converter = NoteTimeConverter::Unmeasured.new(@tempo_computer, sample_rate)
|
22
|
-
end
|
23
|
-
|
24
|
-
it "should return a time of zero when note end is zero." do
|
25
|
-
@converter.time_elapsed(0, 0).should eq(0)
|
26
|
-
end
|
27
|
-
|
28
|
-
it "should return a time of 1 second when note end is equal to the initial notes-per-second" do
|
29
|
-
note_end = @converter.notes_per_second_at(0)
|
30
|
-
@converter.time_elapsed(0, note_end).should eq(1)
|
31
|
-
end
|
32
|
-
end
|
33
|
-
|
34
|
-
context "linear tempo-change" do
|
35
|
-
before :each do
|
36
|
-
@tempo_computer = ValueComputer.new(
|
37
|
-
120, 1 => Change::Gradual.linear(60, 1))
|
38
|
-
sample_rate = 200
|
39
|
-
@converter = NoteTimeConverter::Unmeasured.new(@tempo_computer, sample_rate)
|
40
|
-
end
|
41
|
-
|
42
|
-
it "should return a time of zero when note end is zero." do
|
43
|
-
@converter.time_elapsed(0.0, 0.0).should eq(0.0)
|
44
|
-
end
|
45
|
-
|
46
|
-
it "should return a time of 3 sec during a 1-note long transition from 120bpm to 60bpm" do
|
47
|
-
@converter.notes_per_second_at(1.0).should eq(0.5)
|
48
|
-
@converter.notes_per_second_at(2.0).should eq(0.25)
|
49
|
-
|
50
|
-
@converter.time_elapsed(1.0, 2.0).should be_within(0.05).of(2.77)
|
51
|
-
end
|
52
|
-
|
53
|
-
end
|
54
|
-
end
|
55
|
-
|
56
|
-
describe "#note_time_map" do
|
57
|
-
context "constant tempo" do
|
58
|
-
before :each do
|
59
|
-
@tempo_computer = ValueComputer.new 120
|
60
|
-
sample_rate = 4800
|
61
|
-
@converter = NoteTimeConverter::Unmeasured.new(
|
62
|
-
@tempo_computer, sample_rate)
|
63
|
-
end
|
64
|
-
|
65
|
-
it "should map offset 0.0 to time 0.0" do
|
66
|
-
map = @converter.note_time_map [0.0]
|
67
|
-
map[0.0].should eq(0.0)
|
68
|
-
end
|
69
|
-
|
70
|
-
it "should map offset 0.25 to time 0.5" do
|
71
|
-
map = @converter.note_time_map [0.0, 0.25]
|
72
|
-
map[0.25].should be_within(0.01).of(0.5)
|
73
|
-
end
|
74
|
-
|
75
|
-
it "should map offset 1.0 to time 2.0" do
|
76
|
-
map = @converter.note_time_map [0.0, 1.0]
|
77
|
-
map[1.0].should be_within(0.01).of(2.0)
|
78
|
-
end
|
79
|
-
end
|
80
|
-
end
|
81
|
-
end
|
82
|
-
|
83
|
-
describe NoteTimeConverter::Measured do
|
3
|
+
describe NoteTimeConverter::Tempo do
|
84
4
|
describe '#notes_per_second_at' do
|
85
5
|
it 'should convert tempo using Tempo::BPM.to_nps' do
|
86
6
|
tc = ValueComputer.new(120, 1 => Change::Gradual.linear(100,1),
|
87
7
|
2 => Change::Gradual.linear(150,1))
|
88
8
|
bdc = ValueComputer.new(0.25.to_r, 2.5 => Change::Immediate.new(0.375.to_r))
|
89
|
-
converter = NoteTimeConverter
|
9
|
+
converter = NoteTimeConverter.new(tc,bdc,200)
|
90
10
|
(0..3.2).step(0.2).each do |offset|
|
91
11
|
nps = Tempo::BPM.to_nps(tc.at(offset), bdc.at(offset))
|
92
12
|
converter.notes_per_second_at(offset).should eq(nps)
|
@@ -100,7 +20,7 @@ describe NoteTimeConverter::Measured do
|
|
100
20
|
@tempo_computer = ValueComputer.new 120
|
101
21
|
@bdur_computer = ValueComputer.new Rational(1,4)
|
102
22
|
sample_rate = 48
|
103
|
-
@converter = NoteTimeConverter
|
23
|
+
@converter = NoteTimeConverter.new(@tempo_computer, @bdur_computer, sample_rate)
|
104
24
|
end
|
105
25
|
|
106
26
|
it "should return a time of zero when note end is zero." do
|
@@ -118,7 +38,7 @@ describe NoteTimeConverter::Measured do
|
|
118
38
|
@tempo_computer = ValueComputer.new(120, 1 => Change::Gradual.linear(60, 1))
|
119
39
|
@bdur_computer = ValueComputer.new Rational(1,4)
|
120
40
|
sample_rate = 200
|
121
|
-
@converter = NoteTimeConverter
|
41
|
+
@converter = NoteTimeConverter.new(@tempo_computer, @bdur_computer, sample_rate)
|
122
42
|
end
|
123
43
|
|
124
44
|
it "should return a time of zero when note end is zero." do
|
@@ -141,7 +61,7 @@ describe NoteTimeConverter::Measured do
|
|
141
61
|
@tempo_computer = ValueComputer.new 120
|
142
62
|
@bdur_computer = ValueComputer.new Rational(1,4)
|
143
63
|
sample_rate = 4800
|
144
|
-
@converter = NoteTimeConverter
|
64
|
+
@converter = NoteTimeConverter.new(@tempo_computer, @bdur_computer, sample_rate)
|
145
65
|
end
|
146
66
|
|
147
67
|
it "should map offset 0.0 to time 0.0" do
|
@@ -1,6 +1,6 @@
|
|
1
1
|
require File.expand_path(File.dirname(__FILE__) + '/../../spec_helper')
|
2
2
|
|
3
|
-
describe Score::
|
3
|
+
describe Score::Tempo do
|
4
4
|
before :all do
|
5
5
|
@parts = {
|
6
6
|
"piano" => Part.new(Dynamics::MP,
|
@@ -23,7 +23,7 @@ describe Score::Measured do
|
|
23
23
|
1 => Change::Immediate.new(TWO_FOUR),
|
24
24
|
3 => Change::Immediate.new(SIX_EIGHT)
|
25
25
|
}
|
26
|
-
@score = Score::
|
26
|
+
@score = Score::Tempo.new(THREE_FOUR, 120,
|
27
27
|
parts: @parts,
|
28
28
|
program: @prog,
|
29
29
|
tempo_changes: tcs,
|
@@ -94,7 +94,7 @@ describe Score::Measured do
|
|
94
94
|
context 'meter change at offset 0' do
|
95
95
|
before :all do
|
96
96
|
@change = Change::Immediate.new(THREE_FOUR)
|
97
|
-
@score2 = Score::
|
97
|
+
@score2 = Score::Tempo.new(FOUR_FOUR, 120, meter_changes: { 0 => @change })
|
98
98
|
@mdurs2 = @score2.measure_durations
|
99
99
|
end
|
100
100
|
|
@@ -113,7 +113,7 @@ describe Score::Measured do
|
|
113
113
|
|
114
114
|
context 'no meter changes' do
|
115
115
|
before :all do
|
116
|
-
@score3 = Score::
|
116
|
+
@score3 = Score::Tempo.new(FOUR_FOUR, 120)
|
117
117
|
@mdurs3 = @score3.measure_durations
|
118
118
|
end
|
119
119
|
|
@@ -132,45 +132,10 @@ describe Score::Measured do
|
|
132
132
|
end
|
133
133
|
|
134
134
|
describe '#to_timed' do
|
135
|
-
it 'should use ScoreConverter
|
135
|
+
it 'should use ScoreConverter#convert_score' do
|
136
136
|
nscore1 = @score.to_timed(200)
|
137
|
-
nscore2 = ScoreConverter
|
137
|
+
nscore2 = ScoreConverter.new(@score,200).convert_score
|
138
138
|
nscore1.should eq(nscore2)
|
139
139
|
end
|
140
140
|
end
|
141
141
|
end
|
142
|
-
|
143
|
-
describe Score::Unmeasured do
|
144
|
-
before :all do
|
145
|
-
@parts = {
|
146
|
-
"piano" => Part.new(Dynamics::MP,
|
147
|
-
notes: [Note.quarter(C4), Note.eighth(F3), Note.whole(C4), Note.half(D4)]*12,
|
148
|
-
dynamic_changes: {
|
149
|
-
1 => Change::Immediate.new(Dynamics::MF),
|
150
|
-
5 => Change::Immediate.new(Dynamics::FF),
|
151
|
-
6 => Change::Gradual.linear(Dynamics::MF,2),
|
152
|
-
14 => Change::Immediate.new(Dynamics::PP),
|
153
|
-
}
|
154
|
-
)
|
155
|
-
}
|
156
|
-
@prog = [0...3,4...7,1...20,17..."45/2".to_r]
|
157
|
-
tcs = {
|
158
|
-
0 => Change::Immediate.new(120),
|
159
|
-
4 => Change::Gradual.linear(60,2),
|
160
|
-
11 => Change::Immediate.new(110)
|
161
|
-
}
|
162
|
-
@score = Score::Unmeasured.new(120,
|
163
|
-
parts: @parts,
|
164
|
-
program: @prog,
|
165
|
-
tempo_changes: tcs,
|
166
|
-
)
|
167
|
-
end
|
168
|
-
|
169
|
-
describe '#to_timed' do
|
170
|
-
it 'should use ScoreConverter::Unmeasured#convert_score' do
|
171
|
-
nscore1 = @score.to_timed(200)
|
172
|
-
nscore2 = ScoreConverter::Unmeasured.new(@score,200).convert_score
|
173
|
-
nscore1.should eq(nscore2)
|
174
|
-
end
|
175
|
-
end
|
176
|
-
end
|
@@ -1,15 +1,11 @@
|
|
1
1
|
require File.expand_path(File.dirname(__FILE__) + '/../../spec_helper')
|
2
2
|
|
3
|
-
describe ScoreConverter
|
4
|
-
|
5
|
-
end
|
6
|
-
|
7
|
-
describe ScoreConverter::Measured do
|
3
|
+
describe ScoreConverter do
|
8
4
|
describe '#initialize' do
|
9
5
|
context 'current score is invalid' do
|
10
6
|
it 'should raise NotValidError' do
|
11
|
-
score = Score::
|
12
|
-
expect { ScoreConverter
|
7
|
+
score = Score::Tempo.new(1, 120)
|
8
|
+
expect { ScoreConverter.new(score,200) }.to raise_error(NotValidError)
|
13
9
|
end
|
14
10
|
end
|
15
11
|
end
|
@@ -18,19 +14,19 @@ describe ScoreConverter::Measured do
|
|
18
14
|
before :each do
|
19
15
|
@changeA = Change::Immediate.new(Dynamics::PP)
|
20
16
|
@changeB = Change::Gradual.linear(Dynamics::F, 2)
|
21
|
-
@score = Score::
|
17
|
+
@score = Score::Tempo.new(FOUR_FOUR, 120,
|
22
18
|
parts: {"simple" => Part.new(Dynamics::MP, dynamic_changes: { 1 => @changeA, 3 => @changeB })}
|
23
19
|
)
|
24
20
|
end
|
25
21
|
|
26
22
|
it 'should return Hash with original part names' do
|
27
|
-
parts = ScoreConverter
|
23
|
+
parts = ScoreConverter.new(@score,200).convert_parts
|
28
24
|
parts.should be_a Hash
|
29
25
|
parts.keys.sort.should eq(@score.parts.keys.sort)
|
30
26
|
end
|
31
27
|
|
32
28
|
it 'should convert part dynamic change offsets from measure-based to note-based' do
|
33
|
-
parts = ScoreConverter
|
29
|
+
parts = ScoreConverter.new(@score,200).convert_parts
|
34
30
|
parts.should have_key("simple")
|
35
31
|
part = parts["simple"]
|
36
32
|
part.dynamic_changes.keys.sort.should eq([2,6])
|
@@ -41,7 +37,7 @@ describe ScoreConverter::Measured do
|
|
41
37
|
change.duration.should eq(4)
|
42
38
|
|
43
39
|
#@score.start_meter = THREE_FOUR
|
44
|
-
#parts = ScoreConverter
|
40
|
+
#parts = ScoreConverter.new(@score,200).convert_parts
|
45
41
|
#parts.should have_key("simple")
|
46
42
|
#part = parts["simple"]
|
47
43
|
#part.dynamic_changes.keys.sort.should eq([Rational(3,4),Rational(9,4)])
|
@@ -55,13 +51,13 @@ describe ScoreConverter::Measured do
|
|
55
51
|
|
56
52
|
#context 'gradual changes with positive elapsed and/or remaining' do
|
57
53
|
# it 'should change elapsed and remaining so they reflect note-based offsets' do
|
58
|
-
# score = Score::
|
54
|
+
# score = Score::Tempo.new(THREE_FOUR,120, parts: {
|
59
55
|
# "abc" => Part.new(Dynamics::P, dynamic_changes: {
|
60
56
|
# 2 => Change::Gradual.linear(Dynamics::F,2,1,3),
|
61
57
|
# 7 => Change::Gradual.linear(Dynamics::F,1,4,5)
|
62
58
|
# })
|
63
59
|
# })
|
64
|
-
# converter = ScoreConverter
|
60
|
+
# converter = ScoreConverter.new(score)
|
65
61
|
# parts = converter.convert_parts
|
66
62
|
# dcs = parts["abc"].dynamic_changes
|
67
63
|
#
|
@@ -75,8 +71,8 @@ describe ScoreConverter::Measured do
|
|
75
71
|
describe '#convert_program' do
|
76
72
|
before :each do
|
77
73
|
@prog = [0...4,2...5]
|
78
|
-
@score = Score::
|
79
|
-
@converter = ScoreConverter
|
74
|
+
@score = Score::Tempo.new(FOUR_FOUR, 120, program: @prog)
|
75
|
+
@converter = ScoreConverter.new(@score,200)
|
80
76
|
end
|
81
77
|
|
82
78
|
it 'shuld return array with same size' do
|
@@ -86,7 +82,7 @@ describe ScoreConverter::Measured do
|
|
86
82
|
end
|
87
83
|
|
88
84
|
it 'should convert program segments offsets from measure-based to note-based' do
|
89
|
-
prog = ScoreConverter
|
85
|
+
prog = ScoreConverter.new(@score,200).convert_program
|
90
86
|
prog.size.should eq(2)
|
91
87
|
prog[0].first.should eq(0)
|
92
88
|
prog[0].last.should eq(8)
|
@@ -94,7 +90,7 @@ describe ScoreConverter::Measured do
|
|
94
90
|
prog[1].last.should eq(10)
|
95
91
|
|
96
92
|
@score.start_meter = THREE_FOUR
|
97
|
-
prog = ScoreConverter
|
93
|
+
prog = ScoreConverter.new(@score,200).convert_program
|
98
94
|
prog.size.should eq(2)
|
99
95
|
prog[0].first.should eq(0)
|
100
96
|
prog[0].last.should eq(6)
|
@@ -105,15 +101,15 @@ describe ScoreConverter::Measured do
|
|
105
101
|
|
106
102
|
describe '#convert_score' do
|
107
103
|
it 'should return a timed score' do
|
108
|
-
score = Score::
|
109
|
-
converter = ScoreConverter
|
104
|
+
score = Score::Tempo.new(FOUR_FOUR, 120)
|
105
|
+
converter = ScoreConverter.new(score,200)
|
110
106
|
converter.convert_score.should be_a Score::Timed
|
111
107
|
end
|
112
108
|
|
113
109
|
it 'should use output from convert_program' do
|
114
110
|
prog =[0...4,2...5]
|
115
|
-
score = Score::
|
116
|
-
converter = ScoreConverter
|
111
|
+
score = Score::Tempo.new(FOUR_FOUR, 120, program: prog)
|
112
|
+
converter = ScoreConverter.new(score,200)
|
117
113
|
nscore = converter.convert_score
|
118
114
|
nscore.program.should eq(converter.convert_program)
|
119
115
|
end
|
@@ -121,126 +117,12 @@ describe ScoreConverter::Measured do
|
|
121
117
|
it 'should use output from convert_parts' do
|
122
118
|
changeA = Change::Immediate.new(Dynamics::PP)
|
123
119
|
changeB = Change::Gradual.linear(Dynamics::F, 2)
|
124
|
-
score = Score::
|
120
|
+
score = Score::Tempo.new(FOUR_FOUR, 120,
|
125
121
|
parts: {"simple" => Part.new(Dynamics::MP, dynamic_changes: { 1 => changeA, 3 => changeB })}
|
126
122
|
)
|
127
|
-
converter = ScoreConverter
|
123
|
+
converter = ScoreConverter.new(score,200)
|
128
124
|
nscore = converter.convert_score
|
129
125
|
nscore.parts.should eq(converter.convert_parts)
|
130
126
|
end
|
131
127
|
end
|
132
128
|
end
|
133
|
-
|
134
|
-
describe ScoreConverter::Unmeasured do
|
135
|
-
describe '#initialize' do
|
136
|
-
context 'current score is invalid' do
|
137
|
-
it 'should raise NotValidError' do
|
138
|
-
score = Score::Unmeasured.new(-1)
|
139
|
-
expect { ScoreConverter::Unmeasured.new(score,200) }.to raise_error(NotValidError)
|
140
|
-
end
|
141
|
-
end
|
142
|
-
end
|
143
|
-
|
144
|
-
describe '#convert_parts' do
|
145
|
-
before :each do
|
146
|
-
@changeA = Change::Immediate.new(Dynamics::PP)
|
147
|
-
@changeB = Change::Gradual.linear(Dynamics::F, 2)
|
148
|
-
@score = Score::Unmeasured.new(120,
|
149
|
-
parts: {
|
150
|
-
"normal" => Part.new(Dynamics::MP,
|
151
|
-
dynamic_changes: { 1 => @changeA, 3 => @changeB },
|
152
|
-
notes: "/4C2 /8D2 /8E2 /2C2".to_notes * 4),
|
153
|
-
"empty" => Part.new(Dynamics::PP)
|
154
|
-
}
|
155
|
-
)
|
156
|
-
@parts = ScoreConverter::Unmeasured.new(@score,200).convert_parts
|
157
|
-
end
|
158
|
-
|
159
|
-
it 'should return Hash with original part names' do
|
160
|
-
@parts.should be_a Hash
|
161
|
-
@parts.keys.sort.should eq(@score.parts.keys.sort)
|
162
|
-
end
|
163
|
-
|
164
|
-
it 'should convert part dynamic change offsets from note-based to time-based' do
|
165
|
-
part = @parts["normal"]
|
166
|
-
part.dynamic_changes.keys.sort.should eq([2,6])
|
167
|
-
change = part.dynamic_changes[2.0]
|
168
|
-
change.end_value.should eq(@changeA.end_value)
|
169
|
-
change = part.dynamic_changes[6.0]
|
170
|
-
change.end_value.should eq(@changeB.end_value)
|
171
|
-
change.duration.should eq(4.0)
|
172
|
-
end
|
173
|
-
|
174
|
-
it 'should convert note durations to time durations' do
|
175
|
-
part = @parts["normal"]
|
176
|
-
part.notes.map {|x| x.duration }.should eq([0.5,0.25,0.25,1]*4)
|
177
|
-
end
|
178
|
-
|
179
|
-
context 'trimmed, gradual changes' do
|
180
|
-
it 'should change preceding and remaining so they reflect time-based duration' do
|
181
|
-
score = Score::Unmeasured.new(120, parts: {
|
182
|
-
"abc" => Part.new(Dynamics::P, dynamic_changes: {
|
183
|
-
2 => Change::Gradual.linear(Dynamics::F,4).to_trimmed(2,1),
|
184
|
-
7 => Change::Gradual.linear(Dynamics::F,5).to_trimmed(1,3)
|
185
|
-
})
|
186
|
-
})
|
187
|
-
converter = ScoreConverter::Unmeasured.new(score,200)
|
188
|
-
parts = converter.convert_parts
|
189
|
-
dcs = parts["abc"].dynamic_changes
|
190
|
-
|
191
|
-
dcs.keys.should eq([4,14])
|
192
|
-
dcs[4.0].should eq(Change::Gradual.linear(Dynamics::F,8).to_trimmed(4,2))
|
193
|
-
dcs[14.0].should eq(Change::Gradual.linear(Dynamics::F,10).to_trimmed(2,6))
|
194
|
-
end
|
195
|
-
end
|
196
|
-
end
|
197
|
-
|
198
|
-
describe '#convert_program' do
|
199
|
-
before :each do
|
200
|
-
@prog = [0...4,2...5]
|
201
|
-
@score = Score::Unmeasured.new(120, program: @prog)
|
202
|
-
@converter = ScoreConverter::Unmeasured.new(@score,200)
|
203
|
-
@prog2 = @converter.convert_program
|
204
|
-
end
|
205
|
-
|
206
|
-
it 'should return array with same size' do
|
207
|
-
@prog2.should be_a Array
|
208
|
-
@prog2.size.should eq(@prog.size)
|
209
|
-
end
|
210
|
-
|
211
|
-
it 'should convert program segments offsets from note-based to time-based' do
|
212
|
-
prog = @prog2
|
213
|
-
prog[0].first.should eq(0)
|
214
|
-
prog[0].last.should eq(8)
|
215
|
-
prog[1].first.should eq(4)
|
216
|
-
prog[1].last.should eq(10)
|
217
|
-
end
|
218
|
-
end
|
219
|
-
|
220
|
-
describe '#convert_score' do
|
221
|
-
it 'should return an timed score' do
|
222
|
-
score = Score::Unmeasured.new(120)
|
223
|
-
converter = ScoreConverter::Unmeasured.new(score,200)
|
224
|
-
converter.convert_score.should be_a Score::Timed
|
225
|
-
end
|
226
|
-
|
227
|
-
it 'should use output from convert_program' do
|
228
|
-
prog = [0...4,2...5]
|
229
|
-
score = Score::Unmeasured.new(120, program: prog)
|
230
|
-
converter = ScoreConverter::Unmeasured.new(score,200)
|
231
|
-
nscore = converter.convert_score
|
232
|
-
nscore.program.should eq(converter.convert_program)
|
233
|
-
end
|
234
|
-
|
235
|
-
it 'should use output from convert_parts' do
|
236
|
-
changeA = Change::Immediate.new(Dynamics::PP)
|
237
|
-
changeB = Change::Gradual.linear(Dynamics::F, 2)
|
238
|
-
score = Score::Unmeasured.new(120,
|
239
|
-
parts: {"simple" => Part.new(Dynamics::MP, dynamic_changes: { 1 => changeA, 3 => changeB })}
|
240
|
-
)
|
241
|
-
converter = ScoreConverter::Unmeasured.new(score,200)
|
242
|
-
nscore = converter.convert_score
|
243
|
-
nscore.parts.should eq(converter.convert_parts)
|
244
|
-
end
|
245
|
-
end
|
246
|
-
end
|