# Path: scanner.py
# class ScannerIterator(object):
# 	# string iterator that allows look ahead and push back
# 	# can also push/pop state (for deep lookaheads)
# 	def __init__(self, data):
# 		logger.debug("ScannerIterator datalen=%d", len(data))
# 		self.data = data
# 		self.idx = 0
# 		self.max_idx = len(self.data)
# 		self.state_stack = []
# 
# 	def __iter__(self):
# 		return self
# 
# 	def next(self):
# 		return self.__next__()
# 
# 	def __next__(self):
# 		if self.idx >= self.max_idx:
# 			raise StopIteration
# 		self.idx += 1
# 		return self.data[self.idx-1]
# 
# 	def lookahead(self):
# 		if self.idx >= self.max_idx:
# 			return None
# #		print("lookahead={0}".format(self.data[self.idx]))
# 		return self.data[self.idx]
# 
# 	def pushback(self):
# 		if self.idx <= 0 :
# 			raise StopIteration
# 		self.idx -= 1
# 
# 	def push_state(self):
# 		self.state_stack.append(self.idx)
# #		print( "push stack=", self.state_stack )
# 
# 	def pop_state(self):
# #		print( "pop stack=", self.state_stack )
# 		self.idx = self.state_stack.pop()
# 
# 	def remain(self):
# 		# Test/debug method. Return what remains of the data.
# 		return self.data[self.idx:]
# 
# #	def stop(self):
# #		# truncate the iterator at the current position
# #		assert self.idx < self.max_idx, self.idx
# #
# #		# kill anything after the current position
# #		self.data = self.data[:self.idx]
# #		self.max_idx = len(self.data)
# 
# 	def lstrip(self):
# 		# strip left leading whitespace (like "".strip)
# 		try : 
# 			while str(self.data[self.idx]) in string.whitespace :
# 				self.next()
# 		except IndexError:
# 			raise StopIteration
# 
# 		# allow chaining
# 		return self
# 
# 	def eat(self, s):
# 		# consume a string from the leading part of the data
# 		# for example:  eat("hello") from "hello, world" will result in 
# 		# ", world"
# 		#
# 		# Requires the string be found in the data, like string's index method.
# 		# Requires the string start exactly at the current position.
# 
# 		errmsg = "\"{0}\" not found in {1}".format(s, self)
# 		for c in s :
# 			if self.idx >= self.max_idx:
# 				# full substring not found so error!
# 				raise ValueError(errmsg)
# 
# 			if str(self.data[self.idx]) == c :
# 				self.next()
# 			else :
# 				# full substring not found so error!
# 				raise ValueError(errmsg)
# 
# 		# allow chaining
# 		return self
# 
# Path: printable.py
# def printable_char(c):
# 	if ord(c) < 32:
# 		if c == '\t':
# 			return "\\t"
# 		if c == '\n':
# 			return "\\n"
# 		return "\\x{0:02x}".format(ord(c))
# 	if c == '\\': 
# 		return '\\\\'
# 	if c == '"': 
# 		return '\\"'
# 	return c
# 
# def printable_string(s): 
# 	# Convert a string with unprintable chars and/or weird printing chars into
# 	# something that can be printed without side effects.
# 	# For example, 
# 	#   <tab> -> "\t"   
# 	#   <eol> -> "\n"
# 	#   "	 -> \"
# 	#
# 	# Want to be able to round trip the output of the Symbol hierarchy back
# 	# into valid Python code.
# 	return "".join([printable_char(vc.char) for vc in s if not vc.hide])


import sys
import itertools
import logging
import hexdump
from scanner import ScannerIterator
from printable import printable_char, printable_string

		# save a pristine copy of the original list
		self.phys_lines = phys_lines_list

		# this is where this line blob started in the original source file
		self.starting_file_line = starts_at_file_line

		# create a single array of all the characters with their position in
		# the 2-d array
		self.virt_lines = []
		self._make_virtual_line()

		# Based on the \ line continuation rules, collapse 2-D array into a new
		# 1-D "virtual" array of characters that will be sent to the tokenizer.
		self._collapse_virtual_line()

	def _make_virtual_line(self):
		# Create a 2-D array of VChar from our 2-D array (array of strings).
		#
		# The new 2-D array will be the characters with their row, col in the
		# 2-D array.
		for row_idx, line in enumerate(self.phys_lines):
			vline = []
			for col_idx, char in enumerate(line):
				# char is the original character
				# pos is the (row, col) of the char in the file
				# hide indicates a hidden character (don't feed to the
				# tokenizer, don't highlight in View)
				vchar = VChar(char, (row_idx+self.starting_file_line, col_idx), self.filename)
				vline.append(vchar)

# Path: scanner.py
# class ScannerIterator(object):
# 	# string iterator that allows look ahead and push back
# 	# can also push/pop state (for deep lookaheads)
# 	def __init__(self, data):
# 		logger.debug("ScannerIterator datalen=%d", len(data))
# 		self.data = data
# 		self.idx = 0
# 		self.max_idx = len(self.data)
# 		self.state_stack = []
# 
# 	def __iter__(self):
# 		return self
# 
# 	def next(self):
# 		return self.__next__()
# 
# 	def __next__(self):
# 		if self.idx >= self.max_idx:
# 			raise StopIteration
# 		self.idx += 1
# 		return self.data[self.idx-1]
# 
# 	def lookahead(self):
# 		if self.idx >= self.max_idx:
# 			return None
# #		print("lookahead={0}".format(self.data[self.idx]))
# 		return self.data[self.idx]
# 
# 	def pushback(self):
# 		if self.idx <= 0 :
# 			raise StopIteration
# 		self.idx -= 1
# 
# 	def push_state(self):
# 		self.state_stack.append(self.idx)
# #		print( "push stack=", self.state_stack )
# 
# 	def pop_state(self):
# #		print( "pop stack=", self.state_stack )
# 		self.idx = self.state_stack.pop()
# 
# 	def remain(self):
# 		# Test/debug method. Return what remains of the data.
# 		return self.data[self.idx:]
# 
# #	def stop(self):
# #		# truncate the iterator at the current position
# #		assert self.idx < self.max_idx, self.idx
# #
# #		# kill anything after the current position
# #		self.data = self.data[:self.idx]
# #		self.max_idx = len(self.data)
# 
# 	def lstrip(self):
# 		# strip left leading whitespace (like "".strip)
# 		try : 
# 			while str(self.data[self.idx]) in string.whitespace :
# 				self.next()
# 		except IndexError:
# 			raise StopIteration
# 
# 		# allow chaining
# 		return self
# 
# 	def eat(self, s):
# 		# consume a string from the leading part of the data
# 		# for example:  eat("hello") from "hello, world" will result in 
# 		# ", world"
# 		#
# 		# Requires the string be found in the data, like string's index method.
# 		# Requires the string start exactly at the current position.
# 
# 		errmsg = "\"{0}\" not found in {1}".format(s, self)
# 		for c in s :
# 			if self.idx >= self.max_idx:
# 				# full substring not found so error!
# 				raise ValueError(errmsg)
# 
# 			if str(self.data[self.idx]) == c :
# 				self.next()
# 			else :
# 				# full substring not found so error!
# 				raise ValueError(errmsg)
# 
# 		# allow chaining
# 		return self
# 
# Path: printable.py
# def printable_char(c):
# 	if ord(c) < 32:
# 		if c == '\t':
# 			return "\\t"
# 		if c == '\n':
# 			return "\\n"
# 		return "\\x{0:02x}".format(ord(c))
# 	if c == '\\': 
# 		return '\\\\'
# 	if c == '"': 
# 		return '\\"'
# 	return c
# 
# def printable_string(s): 
# 	# Convert a string with unprintable chars and/or weird printing chars into
# 	# something that can be printed without side effects.
# 	# For example, 
# 	#   <tab> -> "\t"   
# 	#   <eol> -> "\n"
# 	#   "	 -> \"
# 	#
# 	# Want to be able to round trip the output of the Symbol hierarchy back
# 	# into valid Python code.
# 	return "".join([printable_char(vc.char) for vc in s if not vc.hide])


# Path: vline.py
import sys
import itertools
import logging
import hexdump
from scanner import ScannerIterator
from printable import printable_char, printable_string


		# save a pristine copy of the original list
		self.phys_lines = phys_lines_list

		# this is where this line blob started in the original source file
		self.starting_file_line = starts_at_file_line

		# create a single array of all the characters with their position in
		# the 2-d array
		self.virt_lines = []
		self._make_virtual_line()

		# Based on the \ line continuation rules, collapse 2-D array into a new
		# 1-D "virtual" array of characters that will be sent to the tokenizer.
		self._collapse_virtual_line()

	def _make_virtual_line(self):
		# Create a 2-D array of VChar from our 2-D array (array of strings).
		#
		# The new 2-D array will be the characters with their row, col in the
		# 2-D array.
		for row_idx, line in enumerate(self.phys_lines):
			vline = []
			for col_idx, char in enumerate(line):
				# char is the original character
				# pos is the (row, col) of the char in the file
				# hide indicates a hidden character (don't feed to the
				# tokenizer, don't highlight in View)
				vchar = VChar(char, (row_idx+self.starting_file_line, col_idx), self.filename)
				vline.append(vchar)

			self.virt_lines.append(vline)