more clean-up, comments and docs

--HG--
branch : pmacs2
This commit is contained in:
Erik Osheim 2009-07-24 00:07:03 -04:00
parent f2b4dd3712
commit 3c23b94187
4 changed files with 56 additions and 105 deletions

View File

@ -96,14 +96,6 @@ class Application(object):
color.default_color = True color.default_color = True
except: except:
color.default_color = False color.default_color = False
## this is how we can change color settings
#if curses.can_change_color():
# #curses.init_color(28, 700, 0, 0)
# #curses.init_color(29, 0, 0, 700)
# pass
#else:
# self.set_error("Dynamic color not available")
color.init() color.init()
# initialize our modes # initialize our modes
@ -144,7 +136,7 @@ class Application(object):
'latex', 'insertmini', 'conf', 'haskell', 'erlang', 'latex', 'insertmini', 'conf', 'haskell', 'erlang',
'iperl', 'iperlmini', 'ipython', 'ipythonmini', 'awk', 'iperl', 'iperlmini', 'ipython', 'ipythonmini', 'awk',
'shell', 'shellmini', 'fstab', 'yacc', 'pipe', 'shell', 'shellmini', 'fstab', 'yacc', 'pipe',
'mbox', 'error', 'lua', 'lily', 'forth', 'ebnf', 'colortest', 'mbox', 'error', 'lua', 'lily', 'forth', 'ebnf',
) )
for name in names: for name in names:
exec("import mode.%s; mode.%s.install(self)" % (name, name)) exec("import mode.%s; mode.%s.install(self)" % (name, name))
@ -366,14 +358,15 @@ class Application(object):
self.close_buffer(self.get_buffer_by_name(name)) self.close_buffer(self.get_buffer_by_name(name))
def make_name(self, name): def make_name(self, name):
if self.has_buffer_name(name): return util.make_name(name, self.has_buffer_name)
i = 1 #if self.has_buffer_name(name):
auxname = '%s/%d' % (name, i) # i = 1
while self.has_buffer_name(auxname): # auxname = '%s/%d' % (name, i)
i += 1 # while self.has_buffer_name(auxname):
auxname = '%s/%d' % (name, i) # i += 1
name = auxname # auxname = '%s/%d' % (name, i)
return name # name = auxname
#return name
def open_path(self, path, binary=False, cipher=None, password=None): def open_path(self, path, binary=False, cipher=None, password=None):
path = util.literal_path(path) path = util.literal_path(path)
@ -476,7 +469,6 @@ class Application(object):
# buffer handling # buffer handling
def new_file_buffer(self, path, data, switch_to=True): def new_file_buffer(self, path, data, switch_to=True):
assert not self.has_buffer_name(path), '%r is already open' % path assert not self.has_buffer_name(path), '%r is already open' % path
#assert not os.path.exists(path), '%r already exists' % path
# touch the file # touch the file
f = open(path, 'w') f = open(path, 'w')
f.write(data) f.write(data)
@ -506,6 +498,7 @@ class Application(object):
if switch_to: if switch_to:
self.switch_buffer(b) self.switch_buffer(b)
return b return b
# NOTE: make sure that data has escaped \, [, and ] properly, or else you # NOTE: make sure that data has escaped \, [, and ] properly, or else you
# will get undesirable results # will get undesirable results
def color_data_buffer(self, name, data, switch_to=True, modename='colortext'): def color_data_buffer(self, name, data, switch_to=True, modename='colortext'):
@ -540,7 +533,6 @@ class Application(object):
def switch_buffer(self, b): def switch_buffer(self, b):
assert self.has_buffer_name(b.name()), "buffer %s does not exist" % (b.name()) assert self.has_buffer_name(b.name()), "buffer %s does not exist" % (b.name())
assert 0 <= self.active_slot and self.active_slot < len(self.bufferlist.slots) assert 0 <= self.active_slot and self.active_slot < len(self.bufferlist.slots)
#self.add_window_to_buffer(b, self.active_slot)
self.bufferlist.set_slot(self.active_slot, b) self.bufferlist.set_slot(self.active_slot, b)
def add_window_to_buffer(self, b, slotname): def add_window_to_buffer(self, b, slotname):
@ -617,14 +609,15 @@ class Application(object):
# load user configuration NOW # load user configuration NOW
def loadrc(self): def loadrc(self):
path = os.path.join(os.getenv('HOME'), '.pmc', 'conf') path = os.path.join(os.getenv('HOME'), '.pmc', 'conf')
if os.path.exists(path): if not os.path.exists(path):
return
try: try:
f = open(path, 'r') f = open(path, 'r')
exec(f) exec(f)
f.close() f.close()
except Exception, e: except Exception, e:
s = traceback.format_exc() s = traceback.format_exc()
self.rcerror = 'There was an error during startup:\n\n%s' % s self.rcerror = 'There was an error during startup:\n\n' + s
# after actions get handled, do some stuff # after actions get handled, do some stuff
def post_action_hook(self, act): def post_action_hook(self, act):
@ -635,6 +628,7 @@ class Application(object):
else: else:
self.highlight_mark = False self.highlight_mark = False
# UTF-8 aware way to write to the screen
def addstr(self, y, x, s, attr=curses.A_NORMAL): def addstr(self, y, x, s, attr=curses.A_NORMAL):
self.win.addstr(y, x, s.encode('utf-8'), attr) self.win.addstr(y, x, s.encode('utf-8'), attr)
@ -676,7 +670,6 @@ class Application(object):
# clear the error line; it might look confusing to the user # clear the error line; it might look confusing to the user
try: try:
#self.win.addstr(self.y-1, 0, ' ' * self.x)
self.addstr(self.y-1, 0, ' ' * self.x) self.addstr(self.y-1, 0, ' ' * self.x)
except: except:
pass pass
@ -918,10 +911,8 @@ class Application(object):
for hr in self.highlighted_ranges: for hr in self.highlighted_ranges:
(high_w, p1, p2, fg, bg) = hr (high_w, p1, p2, fg, bg) = hr
if w is high_w and p2 >= w.first and p1 <= w.last: if w is high_w and p2 >= w.first and p1 <= w.last:
#raise Exception(repr((slot, p1, p2, fg, bg)))
self.highlight_range(slot, p1, p2, fg, bg) self.highlight_range(slot, p1, p2, fg, bg)
#self.highlight_range(slot, Point(13, 8), Point(29, 8), 'black', 'magenta')
if (self.active_slot == i and not self.highlighted_ranges and self.highlight_mark): if (self.active_slot == i and not self.highlighted_ranges and self.highlight_mark):
fg, bg = 'black', 'cyan' fg, bg = 'black', 'cyan'
cursor = w.logical_cursor() cursor = w.logical_cursor()
@ -936,9 +927,7 @@ class Application(object):
if p1 < w.first: p1 = w.first if p1 < w.first: p1 = w.first
if p2 > w.last: p2 = w.last if p2 > w.last: p2 = w.last
#raise Exception("blargh")
self.highlight_range(slot, p1, p2, fg, bg) self.highlight_range(slot, p1, p2, fg, bg)
#raise Exception("p1=%r p2=%r fg=%r bg=%r" % (p1, p2, fg, bg))
if w.margins_visible: if w.margins_visible:
shade = util.get_margin_color(w, 'blue') shade = util.get_margin_color(w, 'blue')
@ -947,7 +936,6 @@ class Application(object):
for j in range(0, slot.height): for j in range(0, slot.height):
char = chr(self.win.inch(j + slot.y_offset, limit) & 255) char = chr(self.win.inch(j + slot.y_offset, limit) & 255)
attr = color.build('default', shade, 'bold') attr = color.build('default', shade, 'bold')
#self.win.addstr(j + slot.y_offset, limit + w.mode.lmargin, char, attr)
self.addstr(j + slot.y_offset, limit + w.mode.lmargin, char, attr) self.addstr(j + slot.y_offset, limit + w.mode.lmargin, char, attr)
def _draw_slot(self, i): def _draw_slot(self, i):
@ -965,28 +953,27 @@ class Application(object):
# figure out which "physical line" is the first to be shown. note that # figure out which "physical line" is the first to be shown. note that
# the cursor shouldn't be in the last column unless it's the end of a # the cursor shouldn't be in the last column unless it's the end of a
# line. # line.
k = x // swidth k = x // swidth
#if x < len(lines[y]) and x == swidth - 1: #xyz
# k += 1
while count < slot.height: while count < slot.height:
if lit: if lit:
rlines = w.render_line_lit(y, swidth) rlines = w.render_line_lit(y, swidth)
else: else:
rlines = w.render_line_raw(y, swidth) rlines = w.render_line_raw(y, swidth)
for j in range(k, len(rlines)): for j in range(k, len(rlines)):
y2 = slot.y_offset + count
if lm: if lm:
lcont = j > 0 lcont = j > 0
for rstr in slot.window.mode.get_lmargin(w, y, x, ended, lcont): rstrs = slot.window.mode.get_lmargin(w, y, x, ended, lcont)
rstr.draw(self.win, slot.y_offset + count, 0) for rstr in rstrs:
rstr.draw(self.win, y2, 0)
for rstr in rlines[j]: for rstr in rlines[j]:
rstr.draw(self.win, slot.y_offset + count, 0 + lm) rstr.draw(self.win, y2, 0 + lm)
if rm: if rm:
rcont = j < len(rlines) - 1 rcont = j < len(rlines) - 1
for rstr in slot.window.mode.get_rmargin(w, y, x, ended, rcont): rstrs = slot.window.mode.get_rmargin(w, y, x, ended, rcont)
rstr.draw(self.win, slot.y_offset + count, slot.width - rm) for rstr in rstrs:
rstr.draw(self.win, y2, slot.width - rm)
count += 1 count += 1
if count >= slot.height: if count >= slot.height:
break break
@ -1000,7 +987,6 @@ class Application(object):
return return
status = slot.window.mode.get_status_bar() status = slot.window.mode.get_status_bar()
status = status.ljust(slot.width)[:slot.width] status = status.ljust(slot.width)[:slot.width]
#self.win.addstr(slot.height + slot.y_offset, 0, status, curses.A_REVERSE)
self.addstr(slot.height + slot.y_offset, 0, status, curses.A_REVERSE) self.addstr(slot.height + slot.y_offset, 0, status, curses.A_REVERSE)
# input bar drawing # input bar drawing
@ -1012,7 +998,6 @@ class Application(object):
for i in range(0, len(lines)): for i in range(0, len(lines)):
line = lines[i] line = lines[i]
try: try:
#self.win.addstr(self.y - len(lines) + i, 0, line, attr)
self.addstr(self.y - len(lines) + i, 0, line, attr) self.addstr(self.y - len(lines) + i, 0, line, attr)
except: except:
raise raise
@ -1023,7 +1008,6 @@ class Application(object):
for i in range(0, len(plines)): for i in range(0, len(plines)):
pline = plines[i] pline = plines[i]
try: try:
#self.win.addstr(self.y - len(lines) + i, 0, pline, pattr)
self.addstr(self.y - len(lines) + i, 0, pline, pattr) self.addstr(self.y - len(lines) + i, 0, pline, pattr)
except: except:
pass pass
@ -1059,6 +1043,7 @@ def open_aes_file(path, name=None, binary=False):
return buffer.aes.AesBuffer(path, p, name) return buffer.aes.AesBuffer(path, p, name)
else: else:
raise Exception, "can't open %r; unsupported file type" % path raise Exception, "can't open %r; unsupported file type" % path
def open_plain_file(path, name=None, binary=False): def open_plain_file(path, name=None, binary=False):
if os.path.isfile(path) or not os.path.exists(path): if os.path.isfile(path) or not os.path.exists(path):
if binary: if binary:
@ -1080,10 +1065,8 @@ def run_app(stdscr, buffers, **kwargs):
return 0 return 0
if __name__ == "__main__": if __name__ == "__main__":
ciphers = { ciphers = {'none': open_plain_file,
'none': open_plain_file, 'aes': open_aes_file}
'aes': open_aes_file,
}
locale.setlocale(locale.LC_ALL, '') locale.setlocale(locale.LC_ALL, '')
@ -1099,6 +1082,7 @@ if __name__ == "__main__":
else: else:
i += 1 i += 1
# set up the option parser, and set some defaults
import optparse import optparse
parser = optparse.OptionParser() parser = optparse.OptionParser()
parser.set_defaults(debug=False) parser.set_defaults(debug=False)
@ -1177,14 +1161,9 @@ if __name__ == "__main__":
path = os.path.abspath(os.path.realpath(util.expand_tilde(path))) path = os.path.abspath(os.path.realpath(util.expand_tilde(path)))
if path in paths: if path in paths:
continue continue
name = os.path.basename(path)
if name in names: # find a free name that doesn't conflict with any others
i = 1 name = util.make_name(os.path.basename(path), lambda x: x in names)
auxname = '%s/%d' % (name, i)
while auxname in names:
i += 1
auxname = '%s/%d' % (name, i)
name = auxname
try: try:
b = f(path, name, opts.binary) b = f(path, name, opts.binary)

View File

@ -1,37 +0,0 @@
import color
from mode import Fundamental
from lex import Grammar, PatternRule
class ColortestGrammar(Grammar):
rules = []
for i in range(0, 256):
c = '%02x' % i
rules.append(PatternRule('z' + c, c))
class Colortest(Fundamental):
name = 'Colortest'
grammar = ColortestGrammar
colors = {}
def abc(name, r, g, b):
name2 = name + str(r) + str(g) + str(b)
ColortestGrammar.rules.append(PatternRule('z-' + name2, name2))
Colortest.colors['z-' + name2] = (name2, 'default')
for name, r, g, b in color.iter256():
abc(name, r, g, b)
#for i in range(1, 6):
# for j in range(0, i):
# for k in range(0, i):
# abc('red', i, j, k)
# abc('green', j, i, k)
# abc('blue', j, k, i)
#
#for i in range(1, 6):
# for j in range(0, i):
# abc('yellow', i, i, j)
# abc('cyan', j, i, i)
# abc('magenta', i, j, i)
install = Colortest.install

View File

@ -59,13 +59,13 @@ def _make_string_rules(forbidden):
PatternRule('array', r"@\$*" + word2), PatternRule('array', r"@\$*" + word2),
] ]
if forbidden == ')': if forbidden == ')':
rules.append(PatternRule('data', r"\([^\(\)]*\)")) rules.append(PatternRule('data', r"\([^$%@\(\)]*\)"))
elif forbidden == '}': elif forbidden == '}':
rules.append(PatternRule('data', r"{[^{}]*}")) rules.append(PatternRule('data', r"{[^$%@{}]*}"))
elif forbidden == ']': elif forbidden == ']':
rules.append(PatternRule('data', r"\[[^\[\]]*\]")) rules.append(PatternRule('data', r"\[[^$%@\[\]]*\]"))
elif forbidden == '>': elif forbidden == '>':
rules.append(PatternRule('data', r"<[^<>]*>")) rules.append(PatternRule('data', r"<[^$%@<>]*>"))
return rules return rules
class QuotedWords(Grammar): rules = [ class QuotedWords(Grammar): rules = [
@ -85,9 +85,9 @@ class StrictStringGrammar(Grammar): rules = [
PatternRule('data', r"[^\\']+"), PatternRule('data', r"[^\\']+"),
] ]
class StringGrammar(Grammar): class StringGrammar(Grammar):
rules = _make_string_rules('"') + [PatternRule('data', r'[^\\"]+')] rules = _make_string_rules('"') + [PatternRule('data', r'[^$%@\\"]+')]
class EvalGrammar(Grammar): class EvalGrammar(Grammar):
rules = _make_string_rules('`') + [PatternRule('data', r'[^\\`]+')] rules = _make_string_rules('`') + [PatternRule('data', r'[^$%@\\`]+')]
class TranslateGrammar1(Grammar): class TranslateGrammar1(Grammar):
rules = [PatternRule('data', r"(?:\\.|[^\\/])")] rules = [PatternRule('data', r"(?:\\.|[^\\/])")]
@ -226,9 +226,8 @@ class PerlGrammar(Grammar):
RegionRule('perl.quoted', 'q[rqx] *(?P<delim><)', QuotedGrammar3, '>'), RegionRule('perl.quoted', 'q[rqx] *(?P<delim><)', QuotedGrammar3, '>'),
RegionRule('perl.quoted', r'q[rqx] *(?P<delim>\[)', QuotedGrammar4, r'\]'), RegionRule('perl.quoted', r'q[rqx] *(?P<delim>\[)', QuotedGrammar4, r'\]'),
RegionRule('perl.quoted', "q[rqx] *(?P<delim>')", Grammar, "'"), RegionRule('perl.quoted', "q[rqx] *(?P<delim>')", Grammar, "'"),
RegionRule('perl.quoted', 'q[rqx] *(?P<delim>[^ a-zA-Z0-9#])',
MatchGrammar0, '%(delim)s'),
RegionRule('perl.quoted', 'q[rqx](?P<delim>#)', MatchGrammar0, '#'), RegionRule('perl.quoted', 'q[rqx](?P<delim>#)', MatchGrammar0, '#'),
RegionRule('perl.quoted', 'q[rqx] *(?P<delim>[^ a-zA-Z0-9#])', MatchGrammar0, '%(delim)s'),
# quote operator: q() and qw() do not interpolate # quote operator: q() and qw() do not interpolate
RegionRule('perl.quoted', r'qw? *\(', QuotedWords, r'\)'), RegionRule('perl.quoted', r'qw? *\(', QuotedWords, r'\)'),
@ -236,8 +235,7 @@ class PerlGrammar(Grammar):
RegionRule('perl.quoted', 'qw? *<', NoAngle, '>'), RegionRule('perl.quoted', 'qw? *<', NoAngle, '>'),
RegionRule('perl.quoted', r'qw? *\[', NoBracket, r'\]'), RegionRule('perl.quoted', r'qw? *\[', NoBracket, r'\]'),
RegionRule('perl.quoted', 'qw?#', NoHash, '#'), RegionRule('perl.quoted', 'qw?#', NoHash, '#'),
RegionRule('perl.quoted', 'qw? *(?P<delim>[^ a-zA-Z0-9#])', RegionRule('perl.quoted', 'qw? *(?P<delim>[^ a-zA-Z0-9#])', Grammar, '%(delim)s'),
Grammar, '%(delim)s'),
PatternRule('perl.function', word2 + r"(?= *\()"), PatternRule('perl.function', word2 + r"(?= *\()"),
PatternRule('perl.class', word2 + "(?=->)"), PatternRule('perl.class', word2 + "(?=->)"),
@ -722,7 +720,7 @@ class PerlContext(context.Context):
class Perl(Fundamental): class Perl(Fundamental):
name = 'Perl' name = 'Perl'
extensions = ['.pl', '.pm', '.pod'] extensions = ['.pl', '.pm', '.pod', '.t']
detection = [re.compile('^#!(?:.+/)?perl')] detection = [re.compile('^#!(?:.+/)?perl')]
tabbercls = PerlTabber tabbercls = PerlTabber
grammar = PerlGrammar grammar = PerlGrammar

11
util.py
View File

@ -70,6 +70,17 @@ def count_leading_whitespace(s):
assert m, "count leading whitespace failed somehow" assert m, "count leading whitespace failed somehow"
return m.end() - m.start() return m.end() - m.start()
def make_name(name, testf):
'''generate a new name, using testf() to see which names are taken'''
if testf(name):
i = 1
auxname = '%s/%d' % (name, i)
while testf(auxname):
i += 1
auxname = '%s/%d' % (name, i)
name = auxname
return name
# TODO: move these somewhere more sensible. they aren't really utilities. # TODO: move these somewhere more sensible. they aren't really utilities.
def get_margin_limit(w, def_limit=80): def get_margin_limit(w, def_limit=80):
lname = '%s.margin' % w.mode.name.lower() lname = '%s.margin' % w.mode.name.lower()