Class: Beats::SongParser

Inherits:
Object
  • Object
show all
Defined in:
lib/beats/song_parser.rb

Overview

This class is used to parse a raw YAML song definition into domain objects (i.e. Song, Pattern, Track, and Kit). These domain objects can then be used by AudioEngine to generate the actual audio data that is saved to disk.

The sole public method is parse(). It takes a raw YAML string and returns a Song and Kit object (or raises an error if the YAML string couldn’t be parsed correctly).

Defined Under Namespace

Classes: ParseError

Class Method Summary collapse

Class Method Details

.parse(base_path, raw_yaml_string) ⇒ Object

Parses a raw YAML song definition and converts it into a Song and Kit object.



12
13
14
15
16
17
18
19
20
21
22
23
24
25
26
27
28
29
30
31
32
33
34
35
36
37
38
39
40
41
42
43
44
45
46
47
48
49
50
51
52
53
54
55
56
57
58
59
60
61
62
63
64
65
66
67
68
69
70
# File 'lib/beats/song_parser.rb', line 12

def self.parse(base_path, raw_yaml_string)
  raw_song_components = hashify_raw_yaml(raw_yaml_string)

  unless raw_song_components[:folder].nil?
    base_path = raw_song_components[:folder]
  end

  song = Song.new
  kit_builder = KitBuilder.new(base_path)

  # Set tempo
  begin
    unless raw_song_components[:tempo].nil?
      song.tempo = raw_song_components[:tempo]
    end
  rescue Song::InvalidTempoError => detail
    raise ParseError, "#{detail}"
  end

  # Add sounds defined in the Kit section
  begin
    add_kit_sounds_from_kit(kit_builder, raw_song_components[:kit])
  rescue KitBuilder::SoundFileNotFoundError => detail
    raise ParseError, "#{detail}"
  rescue KitBuilder::InvalidSoundFormatError => detail
    raise ParseError, "#{detail}"
  end

  # Load patterns
  add_patterns_to_song(song, kit_builder, raw_song_components[:patterns])

  # Set flow
  if raw_song_components[:flow].nil?
    raise ParseError, "Song must have a Flow section in the header."
  else
    set_song_flow(song, raw_song_components[:flow])
  end

  # Swing, if swing flag is set
  if raw_song_components[:swing]
    begin
      song = Transforms::SongSwinger.transform(song, raw_song_components[:swing])
    rescue Transforms::SongSwinger::InvalidSwingRateError => detail
      raise ParseError, "#{detail}"
    end
  end

  # Build the final kit
  begin
    add_kit_sounds_from_patterns(kit_builder, song.patterns)
    kit = kit_builder.build_kit
  rescue KitBuilder::SoundFileNotFoundError => detail
    raise ParseError, "#{detail}"
  rescue KitBuilder::InvalidSoundFormatError => detail
    raise ParseError, "#{detail}"
  end

  return song, kit
end