DecodeSourceDecodeCommentTags

class Tags

Represents a collection of documentation tags and their parsing logic.

Definitions

def self.build

Build a tags parser with directive mappings.

Signature

parameter block Proc

A block that yields the directives hash.

Implementation

def self.build
	directives = Hash.new
	
	yield directives
	
	return self.new(directives)
end

def initialize(directives)

Initialize a new tags parser.

Signature

parameter directives Hash(String, Class)

The directive mappings.

Implementation

def initialize(directives)
	@directives = directives
end

def valid_indentation?(line, level)

Check if a line has valid indentation for the given level.

Signature

parameter line String

The line to check.

parameter level Integer

The expected indentation level.

Implementation

def valid_indentation?(line, level)
	line.start_with?("  " * level) || line.start_with?("\t" * level)
end

def parse(lines, level = 0, &block)

Parse documentation tags from lines.

Signature

parameter lines Array(String)

The lines to parse.

parameter level Integer

The indentation level.

parameter block Proc

A block to yield parsed tags to.

Implementation

def parse(lines, level = 0, &block)
	while line = lines.first
		# Is it at the right indentation level:
		return unless valid_indentation?(line, level)
		
		# We are going to consume the line:
		lines.shift
		
		# Match it against a tag:
		if match = PATTERN.match(line)
			if klass = @directives[match[:directive]]
				yield klass.parse(
					match[:directive], match[:remainder],
					lines, self, level
				)
			else
				# Ignore unknown directive.
			end
			
		# Or it's just text:
		else
			yield Text.new(line)
		end
	end
end

def ignore(lines, level = 0)

Ignore lines at the specified indentation level.

Signature

parameter lines Array(String)

The lines to ignore.

parameter level Integer

The indentation level.

Implementation

def ignore(lines, level = 0)
	if line = lines.first
		# Is it at the right indentation level:
		return unless valid_indentation?(line, level)
		
		lines.shift
	end
end