musa-dsl 0.23.8 → 0.23.13

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.
Files changed (47) hide show
  1. checksums.yaml +4 -4
  2. data/lib/musa-dsl/core-ext/with.rb +4 -3
  3. data/lib/musa-dsl/datasets/gdv.rb +2 -2
  4. data/lib/musa-dsl/datasets/gdvd.rb +2 -1
  5. data/lib/musa-dsl/datasets/helper.rb +1 -1
  6. data/lib/musa-dsl/datasets/score/queriable.rb +43 -42
  7. data/lib/musa-dsl/datasets/score/render.rb +24 -20
  8. data/lib/musa-dsl/datasets/score/to-mxml/to-mxml.rb +120 -122
  9. data/lib/musa-dsl/generative/backboner.rb +2 -2
  10. data/lib/musa-dsl/generative/generative-grammar.rb +2 -0
  11. data/lib/musa-dsl/generative/markov.rb +1 -2
  12. data/lib/musa-dsl/generative/variatio.rb +6 -10
  13. data/lib/musa-dsl/logger/logger.rb +22 -22
  14. data/lib/musa-dsl/matrix/matrix.rb +3 -5
  15. data/lib/musa-dsl/midi/midi-recorder.rb +3 -4
  16. data/lib/musa-dsl/midi/midi-voices.rb +3 -3
  17. data/lib/musa-dsl/music/chords.rb +26 -29
  18. data/lib/musa-dsl/musicxml/builder/direction.rb +2 -2
  19. data/lib/musa-dsl/neumalang/neumalang.rb +25 -67
  20. data/lib/musa-dsl/neumas/array-to-neumas.rb +2 -2
  21. data/lib/musa-dsl/repl/repl.rb +1 -1
  22. data/lib/musa-dsl/sequencer/base-sequencer-implementation-every.rb +12 -11
  23. data/lib/musa-dsl/sequencer/base-sequencer-implementation-move.rb +53 -52
  24. data/lib/musa-dsl/sequencer/base-sequencer-implementation-play-helper.rb +2 -4
  25. data/lib/musa-dsl/sequencer/base-sequencer-implementation-play-timed.rb +43 -39
  26. data/lib/musa-dsl/sequencer/base-sequencer-implementation-play.rb +5 -7
  27. data/lib/musa-dsl/sequencer/base-sequencer-implementation.rb +6 -14
  28. data/lib/musa-dsl/sequencer/base-sequencer-tick-based.rb +4 -3
  29. data/lib/musa-dsl/sequencer/base-sequencer.rb +5 -5
  30. data/lib/musa-dsl/sequencer/sequencer-dsl.rb +11 -6
  31. data/lib/musa-dsl/series/array-to-serie.rb +5 -3
  32. data/lib/musa-dsl/series/base-series.rb +2 -2
  33. data/lib/musa-dsl/series/buffer-serie.rb +0 -5
  34. data/lib/musa-dsl/series/main-serie-constructors.rb +16 -6
  35. data/lib/musa-dsl/series/main-serie-operations.rb +2 -2
  36. data/lib/musa-dsl/series/quantizer-serie.rb +47 -51
  37. data/lib/musa-dsl/series/series-composer.rb +16 -6
  38. data/lib/musa-dsl/series/timed-serie.rb +49 -48
  39. data/lib/musa-dsl/transcription/from-gdv-to-midi.rb +5 -7
  40. data/lib/musa-dsl/transcription/from-gdv-to-musicxml.rb +1 -4
  41. data/lib/musa-dsl/transcription/from-gdv.rb +1 -3
  42. data/lib/musa-dsl/transcription/transcription.rb +2 -4
  43. data/lib/musa-dsl/transport/input-midi-clock.rb +7 -4
  44. data/lib/musa-dsl/transport/transport.rb +10 -12
  45. data/lib/musa-dsl.rb +1 -1
  46. data/musa-dsl.gemspec +2 -2
  47. metadata +2 -2
@@ -1,6 +1,7 @@
1
1
  require_relative 'base-series'
2
2
 
3
3
  require_relative '../core-ext/with'
4
+ require_relative '../core-ext/arrayfy'
4
5
 
5
6
  module Musa
6
7
  module Series
@@ -10,7 +11,7 @@ module Musa
10
11
  end
11
12
 
12
13
  class ComposerAsOperationSerie
13
- include Serie.with(source: true)
14
+ include Musa::Series::Serie.with(source: true)
14
15
 
15
16
  def initialize(serie, &block)
16
17
  self.source = serie
@@ -68,7 +69,7 @@ module Musa
68
69
  @outputs = {}
69
70
 
70
71
  inputs.keys&.each do |input|
71
- p = PROXY(inputs[input])
72
+ p = Musa::Series::Constructors.PROXY(inputs[input])
72
73
 
73
74
  @inputs[input] = @pipelines[input] = Pipeline.new(input, input: p, output: p.buffered, pipelines: @pipelines)
74
75
 
@@ -76,7 +77,7 @@ module Musa
76
77
  end
77
78
 
78
79
  outputs&.each do |output|
79
- p = PROXY()
80
+ p = Musa::Series::Constructors.PROXY()
80
81
  @outputs[output] = @pipelines[output] = Pipeline.new(output, is_output: true, input: p, output: p, pipelines: @pipelines)
81
82
 
82
83
  @dsl.define_singleton_method(output) { output }
@@ -144,7 +145,7 @@ module Musa
144
145
  end
145
146
 
146
147
  def commit!
147
- first_serie_operation = @first_proc&.call(UNDEFINED())
148
+ first_serie_operation = @first_proc&.call(Musa::Series::Constructors.UNDEFINED())
148
149
 
149
150
  @input ||= first_serie_operation
150
151
 
@@ -282,9 +283,18 @@ module Musa
282
283
  when Proc
283
284
  call_constructor_according_to_last_and_parameter(last.call, constructor, parameter)
284
285
 
286
+ when Musa::Series::Constructors::UndefinedSerie
287
+ case parameter
288
+ when Hash
289
+ Musa::Series::Constructors.method(constructor).call(**parameter)
290
+ when Array
291
+ Musa::Series::Constructors.method(constructor).call(*parameter)
292
+ else
293
+ raise "Unexpected parameter #{parameter} for constructor #{constructor}"
294
+ end
295
+
285
296
  when Serie
286
- # TODO: ignoring last, should make an error?
287
- Musa::Series::Constructors.method(constructor).call(*parameter)
297
+ raise "Unexpected source serie #{last} for constructor #{constructor}"
288
298
 
289
299
  when nil
290
300
  Musa::Series::Constructors.method(constructor).call(*parameter)
@@ -54,13 +54,13 @@ module Musa
54
54
  result = { time: time }
55
55
 
56
56
  @components.each do |attribute_name, components|
57
- if @hash_mode
58
- result[attribute_name] = {}
59
- elsif @array_mode
60
- result[attribute_name] = []
61
- else # value mode
62
- result[attribute_name] = []
63
- end
57
+ result[attribute_name] = if @hash_mode
58
+ {}
59
+ elsif @array_mode
60
+ []
61
+ else # value mode
62
+ []
63
+ end
64
64
 
65
65
  components.each do |target_key_or_index, source_placement|
66
66
  result[attribute_name][target_key_or_index] = selected_values.dig(*source_placement)
@@ -76,67 +76,68 @@ module Musa
76
76
  def infinite?
77
77
  !!@sources.find(&:infinite?)
78
78
  end
79
- end
80
79
 
81
- private def infer_components(sources_values)
82
- other_attributes = Set[]
80
+ private def infer_components(sources_values)
81
+ other_attributes = Set[]
83
82
 
84
- sources_values.each do |source_value|
85
- (source_value.keys - [:time, :value]).each { |_| other_attributes << _ }
86
- end
83
+ sources_values.each do |source_value|
84
+ (source_value.keys - [:time, :value]).each { |_| other_attributes << _ }
85
+ end
87
86
 
88
- components = {}
89
- components[:value] = {}
87
+ components = {}
88
+ components[:value] = {}
90
89
 
91
- hash_mode = array_mode = nil
90
+ hash_mode = array_mode = nil
92
91
 
93
- other_attributes.each do |attribute_name|
94
- components[attribute_name] = {}
95
- end
92
+ other_attributes.each do |attribute_name|
93
+ components[attribute_name] = {}
94
+ end
96
95
 
97
- target_index = 0
96
+ target_index = 0
98
97
 
99
- sources_values.each_with_index do |source_value, i|
100
- case source_value[:value]
101
- when Hash
102
- hash_mode = true
98
+ sources_values.each_with_index do |source_value, i|
99
+ case source_value[:value]
100
+ when Hash
101
+ hash_mode = true
103
102
 
104
- source_value[:value].keys.each do |key|
105
- raise RuntimeError, "Value: key #{key} already used" unless components[:value][key].nil?
103
+ source_value[:value].each_key do |key|
104
+ raise "Value: key #{key} already used" unless components[:value][key].nil?
106
105
 
107
- components[:value][key] = [i, :value, key]
106
+ components[:value][key] = [i, :value, key]
108
107
 
109
- other_attributes.each do |attribute_name|
110
- raise RuntimeError, "Attribute #{attribute_name}: key #{key} already used" unless components[attribute_name][key].nil?
111
- components[attribute_name][key] = [i, attribute_name, key]
108
+ other_attributes.each do |attribute_name|
109
+ raise "Attribute #{attribute_name}: key #{key} already used" unless components[attribute_name][key].nil?
110
+
111
+ components[attribute_name][key] = [i, attribute_name, key]
112
+ end
112
113
  end
113
- end
114
- when Array
115
- array_mode = true
114
+ when Array
115
+ array_mode = true
116
+
117
+ (0..source_value[:value].size - 1).each do |index|
118
+ components[:value][target_index] = [i, :value, index]
119
+
120
+ other_attributes.each do |attribute_name|
121
+ components[attribute_name][target_index] = [i, attribute_name, index]
122
+ end
116
123
 
117
- (0..source_value[:value].size - 1).each do |index|
118
- components[:value][target_index] = [i, :value, index]
124
+ target_index += 1
125
+ end
126
+ else
127
+ components[:value][target_index] = [i, :value]
119
128
 
120
129
  other_attributes.each do |attribute_name|
121
- components[attribute_name][target_index] = [i, attribute_name, index]
130
+ components[attribute_name][target_index] = [i, attribute_name]
122
131
  end
123
132
 
124
133
  target_index += 1
125
134
  end
126
- else
127
- components[:value][target_index] = [i, :value]
128
-
129
- other_attributes.each do |attribute_name|
130
- components[attribute_name][target_index] = [i, attribute_name]
131
- end
132
-
133
- target_index += 1
134
135
  end
135
- end
136
136
 
137
- raise RuntimeError, "source series values are of incompatible type (can't combine Hash and Array values)" if array_mode && hash_mode
137
+ raise "source series values are of incompatible type (can't combine Hash and Array values)" if array_mode && hash_mode
138
138
 
139
- return components, hash_mode, array_mode
139
+ [components, hash_mode, array_mode]
140
+ end
140
141
  end
141
142
 
142
143
  private_constant :TimedUnionOfArrayOfTimedSeries
@@ -170,7 +171,7 @@ module Musa
170
171
  sources_values[key] = @sources_next_values[key] || (@sources_next_values[key] = @sources[key].next_value)
171
172
  end
172
173
 
173
- @other_attributes = infer_other_attributes(sources_values) unless @other_attributes
174
+ @other_attributes ||= infer_other_attributes(sources_values)
174
175
 
175
176
  time = sources_values.values.collect { |_| _&.[](:time) }.compact.min
176
177
 
@@ -1,7 +1,5 @@
1
1
  require_relative 'from-gdv'
2
2
 
3
- include Musa::Transcription
4
-
5
3
  module Musa::Transcriptors
6
4
  module FromGDV
7
5
  module ToMIDI
@@ -15,7 +13,7 @@ module Musa::Transcriptors
15
13
  end
16
14
 
17
15
  # Process: appogiatura (neuma)neuma
18
- class Appogiatura < FeatureTranscriptor
16
+ class Appogiatura < Musa::Transcription::FeatureTranscriptor
19
17
  def transcript(gdv, base_duration:, tick_duration:)
20
18
  gdv_appogiatura = gdv.delete :appogiatura
21
19
 
@@ -34,7 +32,7 @@ module Musa::Transcriptors
34
32
  end
35
33
 
36
34
  # Process: .mor
37
- class Mordent < FeatureTranscriptor
35
+ class Mordent < Musa::Transcription::FeatureTranscriptor
38
36
  def initialize(duration_factor: nil)
39
37
  @duration_factor = duration_factor || 1/4r
40
38
  end
@@ -77,7 +75,7 @@ module Musa::Transcriptors
77
75
  end
78
76
 
79
77
  # Process: .turn
80
- class Turn < FeatureTranscriptor
78
+ class Turn < Musa::Transcription::FeatureTranscriptor
81
79
  def transcript(gdv, base_duration:, tick_duration:)
82
80
  turn = gdv.delete :turn
83
81
 
@@ -118,7 +116,7 @@ module Musa::Transcriptors
118
116
  end
119
117
 
120
118
  # Process: .tr
121
- class Trill < FeatureTranscriptor
119
+ class Trill < Musa::Transcription::FeatureTranscriptor
122
120
  def initialize(duration_factor: nil)
123
121
  @duration_factor = duration_factor || 1/4r
124
122
  end
@@ -195,7 +193,7 @@ module Musa::Transcriptors
195
193
  end
196
194
 
197
195
  # Process: .st .st(1) .st(2) .st(3): staccato level 1 2 3
198
- class Staccato < FeatureTranscriptor
196
+ class Staccato < Musa::Transcription::FeatureTranscriptor
199
197
  def initialize(min_duration_factor: nil)
200
198
  @min_duration_factor = min_duration_factor || 1/8r
201
199
  end
@@ -1,7 +1,5 @@
1
1
  require_relative 'from-gdv'
2
2
 
3
- include Musa::Transcription
4
-
5
3
  module Musa::Transcriptors
6
4
  module FromGDV
7
5
  module ToMusicXML
@@ -11,7 +9,7 @@ module Musa::Transcriptors
11
9
  end
12
10
 
13
11
  # Process: appogiatura (neuma)neuma
14
- class Appogiatura < FeatureTranscriptor
12
+ class Appogiatura < Musa::Transcription::FeatureTranscriptor
15
13
  def transcript(gdv, base_duration:, tick_duration:)
16
14
  if gdv_appogiatura = gdv[:appogiatura]
17
15
  gdv.delete :appogiatura
@@ -30,7 +28,6 @@ module Musa::Transcriptors
30
28
  end
31
29
  end
32
30
  end
33
-
34
31
  end
35
32
  end
36
33
  end
@@ -1,11 +1,9 @@
1
1
  require_relative 'transcription'
2
2
 
3
- include Musa::Transcription
4
-
5
3
  module Musa::Transcriptors
6
4
  module FromGDV
7
5
  # Process: .base .b
8
- class Base < FeatureTranscriptor
6
+ class Base < Musa::Transcription::FeatureTranscriptor
9
7
  def transcript(gdv, base_duration:, tick_duration:)
10
8
  base = gdv.delete :base
11
9
  base ||= gdv.delete :b
@@ -21,8 +21,6 @@ module Musa
21
21
  end
22
22
  end
23
23
 
24
-
25
-
26
24
  element
27
25
  end
28
26
  end
@@ -39,10 +37,10 @@ module Musa
39
37
  element
40
38
  end
41
39
 
42
- def check(value_or_array)
40
+ def check(value_or_array, &block)
43
41
  if block_given?
44
42
  if value_or_array.is_a?(Array)
45
- value_or_array.each { |value| yield value }
43
+ value_or_array.each(&block)
46
44
  else
47
45
  yield value_or_array
48
46
  end
@@ -120,12 +120,15 @@ module Musa
120
120
  yield if block_given? && @started
121
121
 
122
122
  when 'Song Position Pointer'
123
- new_position_in_midi_beats =
124
- m.data[0] & 0x7F | ((m.data[1] & 0x7F) << 7)
123
+ new_position_in_midi_beats = m.data[0] & 0x7F | ((m.data[1] & 0x7F) << 7)
125
124
 
126
- @logger.debug('InputMidiClock') { "processing Song Position Pointer new_position_in_midi_beats #{new_position_in_midi_beats}..." }
125
+ @logger.debug('InputMidiClock') do
126
+ "processing Song Position Pointer new_position_in_midi_beats #{new_position_in_midi_beats}..."
127
+ end
127
128
  @on_change_position.each { |block| block.call midi_beats: new_position_in_midi_beats }
128
- @logger.debug('InputMidiClock') { "processing Song Position Pointer new_position_in_beats #{new_position_in_midi_beats}... done" }
129
+ @logger.debug('InputMidiClock') do
130
+ "processing Song Position Pointer new_position_in_beats #{new_position_in_midi_beats}... done"
131
+ end
129
132
  end
130
133
  end
131
134
  end
@@ -2,12 +2,10 @@ require_relative '../core-ext/smart-proc-binder'
2
2
  require_relative '../core-ext/inspect-nice'
3
3
  require_relative '../sequencer'
4
4
 
5
- using Musa::Extension::InspectNice
6
-
7
5
  module Musa
8
6
  module Transport
9
7
  class Transport
10
- include Musa::Extension::SmartProcBinder
8
+ using Musa::Extension::InspectNice
11
9
 
12
10
  attr_reader :sequencer
13
11
 
@@ -28,20 +26,20 @@ module Musa
28
26
  @clock = clock
29
27
 
30
28
  @before_begin = []
31
- @before_begin << SmartProcBinder.new(before_begin) if before_begin
29
+ @before_begin << Musa::Extension::SmartProcBinder::SmartProcBinder.new(before_begin) if before_begin
32
30
 
33
31
  @on_start = []
34
- @on_start << SmartProcBinder.new(on_start) if on_start
32
+ @on_start << Musa::Extension::SmartProcBinder::SmartProcBinder.new(on_start) if on_start
35
33
 
36
34
  @on_change_position = []
37
- @on_change_position << SmartProcBinder.new(on_position_change) if on_position_change
35
+ @on_change_position << Musa::Extension::SmartProcBinder::SmartProcBinder.new(on_position_change) if on_position_change
38
36
 
39
37
  @after_stop = []
40
- @after_stop << SmartProcBinder.new(after_stop) if after_stop
38
+ @after_stop << Musa::Extension::SmartProcBinder::SmartProcBinder.new(after_stop) if after_stop
41
39
 
42
40
  @do_log = do_log
43
41
 
44
- @sequencer = Sequencer::Sequencer.new beats_per_bar, ticks_per_beat, logger: logger, do_log: @do_log
42
+ @sequencer = Musa::Sequencer::Sequencer.new beats_per_bar, ticks_per_beat, logger: logger, do_log: @do_log
45
43
 
46
44
  @clock.on_start do
47
45
  do_on_start
@@ -57,19 +55,19 @@ module Musa
57
55
  end
58
56
 
59
57
  def before_begin(&block)
60
- @before_begin << SmartProcBinder.new(block)
58
+ @before_begin << Musa::Extension::SmartProcBinder::SmartProcBinder.new(block)
61
59
  end
62
60
 
63
61
  def on_start(&block)
64
- @on_start << SmartProcBinder.new(block)
62
+ @on_start << Musa::Extension::SmartProcBinder::SmartProcBinder.new(block)
65
63
  end
66
64
 
67
65
  def after_stop(&block)
68
- @after_stop << SmartProcBinder.new(block)
66
+ @after_stop << Musa::Extension::SmartProcBinder::SmartProcBinder.new(block)
69
67
  end
70
68
 
71
69
  def on_change_position(&block)
72
- @on_change_position << SmartProcBinder.new(block)
70
+ @on_change_position << Musa::Extension::SmartProcBinder::SmartProcBinder.new(block)
73
71
  end
74
72
 
75
73
  def start
data/lib/musa-dsl.rb CHANGED
@@ -1,5 +1,5 @@
1
1
  module Musa
2
- VERSION = '0.23.0'
2
+ VERSION = '0.23.13'
3
3
  end
4
4
 
5
5
  require_relative 'musa-dsl/core-ext'
data/musa-dsl.gemspec CHANGED
@@ -1,7 +1,7 @@
1
1
  Gem::Specification.new do |s|
2
2
  s.name = 'musa-dsl'
3
- s.version = '0.23.8'
4
- s.date = '2021-08-03'
3
+ s.version = '0.23.13'
4
+ s.date = '2021-09-02'
5
5
  s.summary = 'A simple Ruby DSL for making complex music'
6
6
  s.description = 'Musa-DSL: A Ruby framework and DSL for algorithmic sound and musical thinking and composition'
7
7
  s.authors = ['Javier Sánchez Yeste']
metadata CHANGED
@@ -1,14 +1,14 @@
1
1
  --- !ruby/object:Gem::Specification
2
2
  name: musa-dsl
3
3
  version: !ruby/object:Gem::Version
4
- version: 0.23.8
4
+ version: 0.23.13
5
5
  platform: ruby
6
6
  authors:
7
7
  - Javier Sánchez Yeste
8
8
  autorequire:
9
9
  bindir: bin
10
10
  cert_chain: []
11
- date: 2021-08-03 00:00:00.000000000 Z
11
+ date: 2021-09-02 00:00:00.000000000 Z
12
12
  dependencies:
13
13
  - !ruby/object:Gem::Dependency
14
14
  name: citrus