Class: Parsby::PosRange

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

Direct Known Subclasses

ParsedRange

Instance Attribute Summary collapse

Instance Method Summary collapse

Constructor Details

#initialize(pos_start, pos_end) ⇒ PosRange

PosRanges are constructed with a starting and ending position. We consider the starting position to be inside the range, and the ending position to be outside the range. So, if start is 1 and end is 2, then only position 1 is inside the range. If start is 1 and end is 1, then there is no position inside the range.



17
18
19
20
# File 'lib/parsby.rb', line 17

def initialize(pos_start, pos_end)
  @start = pos_start
  @end = pos_end
end

Instance Attribute Details

#endObject

Returns the value of attribute end.



10
11
12
# File 'lib/parsby.rb', line 10

def end
  @end
end

#startObject

Returns the value of attribute start.



10
11
12
# File 'lib/parsby.rb', line 10

def start
  @start
end

Instance Method Details

#&(range) ⇒ Object

Intersection of two ranges. Touching ranges result in a range of length 0.



34
35
36
37
# File 'lib/parsby.rb', line 34

def &(range)
  return nil unless overlaps?(range) || touching?(range)
  PosRange.new [@start, range.start].max, [@end, range.end].min
end

#completely_inside_of?(range) ⇒ Boolean

Returns:

  • (Boolean)


71
72
73
# File 'lib/parsby.rb', line 71

def completely_inside_of?(range)
  starts_inside_of?(range) && ends_inside_of?(range)
end

#completely_left_of?(range) ⇒ Boolean

Returns:

  • (Boolean)


51
52
53
# File 'lib/parsby.rb', line 51

def completely_left_of?(range)
  @end <= range.start
end

#completely_right_of?(range) ⇒ Boolean

Returns:

  • (Boolean)


55
56
57
# File 'lib/parsby.rb', line 55

def completely_right_of?(range)
  range.end <= @start
end

#contains?(pos) ⇒ Boolean

Returns:

  • (Boolean)


59
60
61
# File 'lib/parsby.rb', line 59

def contains?(pos)
  @start <= pos && pos < @end
end

#ends_inside_of?(range) ⇒ Boolean

Returns:

  • (Boolean)


67
68
69
# File 'lib/parsby.rb', line 67

def ends_inside_of?(range)
  range.contains?(@end) || range.end == @end
end

#lengthObject

Length of range.



23
24
25
# File 'lib/parsby.rb', line 23

def length
  @end - @start
end

#length_in(range) ⇒ Object

Length of overlap. 0 for non-overlapping ranges.



28
29
30
# File 'lib/parsby.rb', line 28

def length_in(range)
  (self & range)&.length || 0
end

#overlaps?(range) ⇒ Boolean

True when one is not completely left of or right of the other. Touching ranges do not overlap, even though they have an intersection range of length 0.

Returns:

  • (Boolean)


47
48
49
# File 'lib/parsby.rb', line 47

def overlaps?(range)
  !(completely_left_of?(range) || completely_right_of?(range))
end

#render_in(line_range) ⇒ Object



75
76
77
78
79
80
81
82
83
84
85
# File 'lib/parsby.rb', line 75

def render_in(line_range)
  return "<-" if completely_left_of?(line_range) && !starts_inside_of?(line_range)
  return "->" if completely_right_of? line_range
  indentation = " " * [0, start - line_range.start].max
  r = "-" * length_in(line_range)
  r[0] = "\\" if starts_inside_of? line_range
  r[-1] = "/" if ends_inside_of? line_range
  r[0] = "|" if length_in(line_range) == 0
  r[0] = "V" if length_in(line_range) == 1 && completely_inside_of?(line_range)
  indentation + r
end

#starts_inside_of?(range) ⇒ Boolean

Returns:

  • (Boolean)


63
64
65
# File 'lib/parsby.rb', line 63

def starts_inside_of?(range)
  range.contains? @start
end

#touching?(range) ⇒ Boolean

True when the end of one is the beginning of the other.

Returns:

  • (Boolean)


40
41
42
# File 'lib/parsby.rb', line 40

def touching?(range)
  range.end == self.start || self.end == range.start
end