class Savage::Parser
Constants
- DIRECTIONS
Public Class Methods
parse(parsable)
click to toggle source
# File lib/savage/parser.rb, line 25 def parse(parsable) raise TypeError if parsable.class != String subpaths = extract_subpaths parsable raise TypeError if (subpaths.empty?) path = Path.new path.subpaths = [] subpaths.each_with_index do |subpath, i| path.subpaths << parse_subpath(subpath, i == 0) end path end
Private Class Methods
build_direction(parsable, force_absolute=false)
click to toggle source
# File lib/savage/parser.rb, line 72 def build_direction(parsable, force_absolute=false) directions = [] @coordinates = extract_coordinates parsable recurse_code = parsable[0,1] first_absolute = force_absolute # we need to handle this separately, since ClosePath doesn't take any coordinates if @coordinates.empty? && recurse_code =~ /[Zz]/ directions << Directions::ClosePath.new(parsable[0,1] == parsable[0,1].upcase) end until @coordinates.empty? absolute = (first_absolute || parsable[0,1] == parsable[0,1].upcase) directions << construct_direction(recurse_code.strip[0].downcase.intern, absolute) recurse_code = 'L' if recurse_code.downcase =~ /m/ first_absolute = false end directions end
construct_direction(recurse_code, absolute)
click to toggle source
# File lib/savage/parser.rb, line 93 def construct_direction(recurse_code, absolute) args = @coordinates.shift DIRECTIONS[recurse_code][:args] raise TypeError if args.any?(&:nil?) DIRECTIONS[recurse_code][:class].new(*args, absolute) end
extract_coordinates(command_string)
click to toggle source
# File lib/savage/parser.rb, line 99 def extract_coordinates(command_string) coordinates = [] command_string.scan(/-?\d+(\.\d+)?([eE][+-]?\d+)?/) do |match_group| coordinates << $&.to_f end coordinates end
extract_directions(parsable, force_absolute=false)
click to toggle source
# File lib/savage/parser.rb, line 57 def extract_directions(parsable, force_absolute=false) directions = [] i = 0 parsable.scan(/[MmLlHhVvQqCcTtSsAaZz](?:\d|[eE.,+-]|\W)*/m) do |match_group| direction = build_direction $&, force_absolute && i == 0 if direction.kind_of?(Array) directions.concat direction else directions << direction end i += 1 end directions end
extract_subpaths(parsable)
click to toggle source
# File lib/savage/parser.rb, line 38 def extract_subpaths(parsable) subpaths = [] if move_index = parsable.index(/[Mm]/) subpaths << parsable[0...move_index] if move_index > 0 parsable.scan(/[Mm](?:\d|[eE.,+-]|[LlHhVvQqCcTtSsAaZz]|\W)+/m) do |match_group| subpaths << $& end else subpaths << parsable end subpaths end
parse_subpath(parsable, force_absolute=false)
click to toggle source
# File lib/savage/parser.rb, line 51 def parse_subpath(parsable, force_absolute=false) subpath = SubPath.new subpath.directions = extract_directions parsable, force_absolute subpath end