--HG--
branch : pmacs2
This commit is contained in:
moculus 2008-04-07 02:31:13 +00:00
parent cfac74acab
commit 406331e650
9 changed files with 131 additions and 66 deletions

4
IDEAS
View File

@ -1,3 +1,7 @@
2008/04/06:
line numbers/margin support
2008/04/02: 2008/04/02:
fix read-only warnings to seem less junky (e.g. catch the buffer.ReadOnlyError fix read-only warnings to seem less junky (e.g. catch the buffer.ReadOnlyError

View File

@ -522,9 +522,7 @@ class Application(object):
self.draw_slots() self.draw_slots()
self.draw_input_bar() self.draw_input_bar()
self.draw_cursor() self.draw_cursor()
#self.win.noutrefresh() self.win.refresh()
#curses.doupdate()
curses.refresh()
except Exception, e: except Exception, e:
# ok, so there was a problem... # ok, so there was a problem...
# let's see if the screen changed sizes and if so, resize our slots # let's see if the screen changed sizes and if so, resize our slots
@ -558,7 +556,8 @@ class Application(object):
(vy, vx) = (None, None) (vy, vx) = (None, None)
while count < slot.height: while count < slot.height:
if p.y == y and p.x >= x and p.x <= x + slot.width: if p.y == y and p.x >= x and p.x <= x + slot.width:
(vy, vx) = (slot.offset + count, p.x - x) #(vy, vx) = (slot.y_offset + count, p.x - x + slot.lmargin)
(vy, vx) = (slot.y_offset + count, p.x - x + w.mode.lmargin)
break break
if x + slot.width >= len(w.buffer.lines[y]): if x + slot.width >= len(w.buffer.lines[y]):
x = 0 x = 0
@ -610,6 +609,7 @@ class Application(object):
self._draw_slot_lit(i) self._draw_slot_lit(i)
else: else:
self._draw_slot_raw(i) self._draw_slot_raw(i)
self.draw_slot_margins(i)
# highlighted regions # highlighted regions
for (high_w, p1, p2, fg, bg) in self.highlighted_ranges: for (high_w, p1, p2, fg, bg) in self.highlighted_ranges:
@ -620,10 +620,12 @@ class Application(object):
while count < slot.height: while count < slot.height:
if p1.y == y and px >= x and px - x < slot.width: if p1.y == y and px >= x and px - x < slot.width:
if slot.width > p2.x - x: if slot.width > p2.x - x:
self.highlight_chars(slot.offset + count, px-x, p2.x-x, fg, bg) #self.highlight_chars(slot.y_offset + count, px-x + slot.lmargin, p2.x-x, fg, bg)
self.highlight_chars(slot.y_offset + count, px-x + w.mode.lmargin, p2.x-x, fg, bg)
break break
else: else:
self.highlight_chars(slot.offset + count, px-x, slot.width, fg, bg) #self.highlight_chars(slot.y_offset + count, px-x + slot.lmargin, slot.width, fg, bg)
self.highlight_chars(slot.y_offset + count, px-x + w.mode.lmargin, slot.width, fg, bg)
px += slot.width - px + x px += slot.width - px + x
if x + slot.width >= len(w.buffer.lines[y]): if x + slot.width >= len(w.buffer.lines[y]):
x = 0 x = 0
@ -634,12 +636,29 @@ class Application(object):
if w.margins_visible: if w.margins_visible:
for (limit, shade) in w.margins: for (limit, shade) in w.margins:
#if limit <= self.x:
if limit < self.x: if limit < self.x:
for j in range(0, slot.height): for j in range(0, slot.height):
char = chr(self.win.inch(j + slot.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.offset, limit, char, attr) #self.win.addstr(j + slot.y_offset, limit + slot.lmargin, char, attr)
self.win.addstr(j + slot.y_offset, limit + w.mode.lmargin, char, attr)
def draw_slot_margins(self, i):
slot = self.bufferlist.slots[i]
w = slot.window
b = w.buffer
#x = slot.lmargin + slot.width + 1
x = w.mode.lmargin + slot.width + 1
for i in range(0, slot.height):
y = i + slot.y_offset
#if slot.lmargin:
if w.mode.lmargin:
(lmargin, lattr) = w.mode.get_lmargin(i)
self.win.addstr(y, 0, lmargin, lattr)
#if slot.rmargin:
if w.mode.rmargin:
(rmargin, rattr) = w.mode.get_rmargin(i)
self.win.addstr(y, x, rmargin, rattr)
def _draw_slot_raw(self, i): def _draw_slot_raw(self, i):
slot = self.bufferlist.slots[i] slot = self.bufferlist.slots[i]
@ -648,26 +667,33 @@ class Application(object):
redattr = color.build_attr(color.pairs('red', 'default')) redattr = color.build_attr(color.pairs('red', 'default'))
(x, y) = w.first.xy() (x, y) = w.first.xy()
lines = w.buffer.lines lines = w.buffer.lines
count = 0 count = 0
swidth = slot.width - w.mode.lmargin - w.mode.rmargin
while count < slot.height: while count < slot.height:
if y >= len(lines): if y >= len(lines):
self.win.addstr(slot.offset + count, 0, '~', redattr) #self.win.addstr(slot.y_offset + count, 0 + slot.lmargin, '~', redattr)
self.win.addstr(slot.y_offset + count, 0 + w.mode.lmargin, '~', redattr)
count += 1 count += 1
continue continue
line = lines[y] line = lines[y]
s = line[x:x + slot.width] #s = line[x:x + slot.width]
s = line[x:x + swidth]
try: try:
self.win.addstr(slot.offset + count, 0, s) #self.win.addstr(slot.y_offset + count, 0 + slot.lmargin, s)
self.win.addstr(slot.y_offset + count, 0 + w.mode.lmargin, s)
except: except:
self.set_error("addstr(%r + %r, %r, %r)" % (slot.offset, count, 0, s)) #self.set_error("addstr(%r+%r, %r+%r, %r)" % (slot.y_offset, count, 0, slot.lmargin, s))
if x + slot.width >= len(line): self.set_error("addstr(%r+%r, %r+%r, %r)" % (slot.y_offset, count, 0, w.mode.lmargin, s))
#if x + slot.width >= len(line):
if x + swidth >= len(line):
x = 0 x = 0
y += 1 y += 1
else: else:
self.win.addstr(slot.offset + count, slot.width, '\\', redattr) #self.win.addstr(slot.y_offset + count, slot.width + slot.lmargin, '\\', redattr)
x += slot.width self.win.addstr(slot.y_offset + count, swidth + w.mode.lmargin, '\\', redattr)
x += swidth
count += 1 count += 1
def _draw_slot_lit(self, i): def _draw_slot_lit(self, i):
@ -694,21 +720,24 @@ class Application(object):
s_offset = max(x - token.x, 0) s_offset = max(x - token.x, 0)
x_offset = max(token.x - x, 0) x_offset = max(token.x - x, 0)
assert x_offset <= slot.width, '%d <= %d' % (x_offset, slot.width) swidth = slot.width - w.mode.lmargin - w.mode.rmargin
assert x_offset <= swidth, '%d <= %d' % (x_offset, swidth)
s = tstring[s_offset:] s = tstring[s_offset:]
token_done = x_offset + len(s) <= slot.width token_done = x_offset + len(s) <= swidth
token_wrap = x_offset + len(s) > slot.width token_wrap = x_offset + len(s) > swidth
# for debugging things like lexing/relexing/etc. # for debugging things like lexing/relexing/etc.
if token._debug: if token._debug:
attr = color.build('blue', 'green') attr = color.build('blue', 'green')
else: else:
attr = color.build(*token.color) attr = color.build(*token.color)
self.win.addstr(slot.offset + count, x_offset, s[:slot.width - x_offset], attr) #self.win.addstr(slot.y_offset + count, x_offset + slot.lmargin, s[:slot.width - x_offset], attr)
self.win.addstr(slot.y_offset + count, x_offset + w.mode.lmargin, s[:swidth - x_offset], attr)
if token_wrap: if token_wrap:
self.win.addstr(slot.offset + count, slot.width, '\\', redattr) #self.win.addstr(slot.y_offset + count, slot.width + slot.lmargin, '\\', redattr)
x += slot.width self.win.addstr(slot.y_offset + count, swidth + w.mode.lmargin, '\\', redattr)
x += swidth
count += 1 count += 1
if token_done: if token_done:
j += 1 j += 1
@ -717,10 +746,11 @@ class Application(object):
# we have finished this logical line of tokens # we have finished this logical line of tokens
j = x = 0 j = x = 0
y += 1 y += 1
count += 1 count += 1
else: else:
self.win.addstr(slot.offset + count, 0, '~', redattr) #self.win.addstr(slot.y_offset + count, 0 + slot.lmargin, '~', redattr)
self.win.addstr(slot.y_offset + count, 0 + w.mode.lmargin, '~', redattr)
count += 1 count += 1
def draw_status_bar(self, slotname): def draw_status_bar(self, slotname):
@ -758,15 +788,12 @@ class Application(object):
else: else:
perc = "%2d%%" % (first.y*100 / len(b.lines)) perc = "%2d%%" % (first.y*100 / len(b.lines))
# XYZ: we should actually use more of the 'state' variables # XYZ: we should actually use more of the 'state' variables
format = "%s %-18s (%s)--L%d--C%d--%s" format = "%s %-18s (%s)--L%d--C%d--%s"
status = format % (modflag, name, w.mode.name(), cursor.y+1, cursor.x+1, perc) status = format % (modflag, name, w.mode.name(), cursor.y+1, cursor.x+1, perc)
#format = "%s %-18s (%s)--L%d--C%d--%s %s %s %s" status = status.ljust(slot.total_width + 1)[:slot.total_width + 1]
#status = format % (modflag, name, w.mode.name(), cursor.y+1, cursor.x+1, perc, w.first, cursor, w.last)
status = status.ljust(slot.width + 1)[:slot.width + 1] self.win.addstr(slot.height + slot.y_offset, 0, status, curses.A_REVERSE)
self.win.addstr(slot.height + slot.offset, 0, status, curses.A_REVERSE)
# input bar drawing # input bar drawing
def draw_input_bar(self): def draw_input_bar(self):
@ -874,12 +901,6 @@ if __name__ == "__main__":
# first file on line 19 (same as -g 19 or --goto 19) # first file on line 19 (same as -g 19 or --goto 19)
if goto_line: if goto_line:
opts.goto = goto_line opts.goto = goto_line
#if len(args) > 0 and args[0].startswith('+'):
# opts.goto = int(args[0][1:])
# args = args[1:]
#if opts.goto is not None:
# opts.goto += 1
# figure out which kind of line types we're using # figure out which kind of line types we're using
if opts.linetype not in linetypes: if opts.linetype not in linetypes:
@ -897,8 +918,7 @@ if __name__ == "__main__":
buffers = [] buffers = []
names = sets.Set() names = sets.Set()
paths = sets.Set() paths = sets.Set()
#if not args:
# args = ['.']
for path in args: for path in args:
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:

View File

@ -2,6 +2,8 @@ import datetime, grp, md5, os, pwd, re, sets, shutil, stat, string
import aes, dirutil, regex, highlight, lex import aes, dirutil, regex, highlight, lex
from point import Point from point import Point
#from point import Pointfrom point import Pointfrom point import Pointfrom point import Pointfrom point import Pointfrom point import Pointfrom point import Pointfrom point import Pointfrom point import Pointfrom point import Pointfrom point import Pointfrom point import Pointfrom point import Pointfrom point import Pointfrom point import Point
# undo/redo stack constants # undo/redo stack constants
ACT_NORM = 0 ACT_NORM = 0
ACT_UNDO = 1 ACT_UNDO = 1

View File

@ -2,21 +2,26 @@ import sets
import window import window
class Slot(object): class Slot(object):
def __init__(self, height, width, offset): def __init__(self, height, width, y_offset=0, x_offset=0):
self.height = height self.window = None
self.width = width self.lmargin = 0
self.offset = offset self.rmargin = 0
self.window = None self.resize(height, width, y_offset, x_offset)
def is_empty(self): def is_empty(self):
return self.window is None return self.window is None
def resize(self, height, width, offset): def resize(self, height, width, y_offset=0, x_offset=0):
self.height = height self.height = height
self.width = width self.total_width = width
self.offset = offset self.width = width - self.lmargin - self.rmargin
self.y_offset = y_offset
self.x_offset = x_offset
if self.window is not None: if self.window is not None:
self.window.set_size(self.width, self.height) self.window.set_size(self.width, self.height)
def set(self, w): def set(self, w):
self.window = w self.window = w
self.lmargin = w.mode.lmargin
self.rmargin = w.mode.rmargin
self.resize(self.height, self.width, self.y_offset, self.x_offset)
w.set_size(self.width, self.height) w.set_size(self.width, self.height)
def unset(self): def unset(self):
if not self.is_empty(): if not self.is_empty():

View File

@ -8,7 +8,9 @@ sub foo {
} }
#@@:heredoc:sql #@@:heredoc:sql
#@@:heredoc.string:xml
my $s = <<EOT; my $s = <<EOT;
select '<foo attr="3">bar bar</foo>';
drop table foog; drop table foog;
insert into mytable (col1, col2, "col3") values (99, 33, 1234); insert into mytable (col1, col2, "col3") values (99, 33, 1234);
select cast(plunk as timestamp) from blarg join plarg using(id_what) where x = 3; select cast(plunk as timestamp) from blarg join plarg using(id_what) where x = 3;

View File

@ -964,6 +964,15 @@ class SetConfigVariable(Method):
else: else:
w.set_error("previously unset param %r set to %r" % (name, value)) w.set_error("previously unset param %r set to %r" % (name, value))
class ToggleLineNumbers(Method):
def _execute(self, w, **vargs):
if w.mode.show_line_numbers:
w.mode.disable_line_numbers()
w.set_error('Line numbers hidden')
else:
w.mode.enable_line_numbers()
w.set_error('Line numbers visible')
class SetTabWidth(Method): class SetTabWidth(Method):
args = [arg('width', t=type(0), p="Tab Width: ", h='New tab width for buffer')] args = [arg('width', t=type(0), p="Tab Width: ", h='New tab width for buffer')]
def _execute(self, w, **vargs): def _execute(self, w, **vargs):

View File

@ -88,6 +88,11 @@ class Fundamental(Handler):
colors = {} colors = {}
config = {} config = {}
# margin/line numbering
show_line_numbers = False
lmargin = 0
rmargin = 0
def install(cls, app): def install(cls, app):
app.setmode(cls.modename.lower(), cls, paths=cls.paths, app.setmode(cls.modename.lower(), cls, paths=cls.paths,
basenames=cls.basenames, extensions=cls.extensions, basenames=cls.basenames, extensions=cls.extensions,
@ -188,6 +193,9 @@ class Fundamental(Handler):
self.add_bindings('insert-squotes', ('M-\'',)) self.add_bindings('insert-squotes', ('M-\'',))
self.add_bindings('insert-dquotes', ('M-"',)) self.add_bindings('insert-dquotes', ('M-"',))
self.add_bindings('get-token', ('C-c t',)) self.add_bindings('get-token', ('C-c t',))
self.add_bindings('insert-text', ('C-c i',))
self.add_bindings('insert-text2', ('C-c M-i',))
self.add_bindings('insert-multiline-text', ('C-c m',))
# create all the insert actions for the basic text input # create all the insert actions for the basic text input
for c in string.letters + string.digits + string.punctuation: for c in string.letters + string.digits + string.punctuation:
@ -205,6 +213,24 @@ class Fundamental(Handler):
if self.tabbercls: if self.tabbercls:
self.tabber = self.tabbercls(self) self.tabber = self.tabbercls(self)
def enable_line_numbers(self):
self.show_line_numbers = True
self.lmargin = 4
self.get_lmargin = self._line_number_margin
def disable_line_numbers(self):
self.show_line_numbers = False
self.lmargin = 0
self.get_lmargin = self._null_margin
def get_rmargin(self, i):
return ('', color.build('default', 'default'))
def _null_margin(self, i):
return ('', color.build('default', 'default'))
def _line_number_margin(self, i):
return ('% 3d ' % i, color.build('default', 'default', 'bold'))
get_lmargin = _null_margin
get_rmargin = _null_margin
# get mode name # get mode name
def name(self): def name(self):
return self.modename return self.modename

View File

@ -41,32 +41,29 @@ class InsertMini(mode.Fundamental):
self.add_bindings('delete-right-whitespace', ('C-c d',)) self.add_bindings('delete-right-whitespace', ('C-c d',))
self.add_bindings('insert-space', ('SPACE',)) self.add_bindings('insert-space', ('SPACE',))
self.add_bindings('insert-tab', ('TAB',)) self.add_bindings('insert-tab', ('TAB',))
self.add_action_and_bindings(InsertExec(), ('RETURN',)) self.add_action_and_bindings(InsertLine(), ('RETURN',))
self.add_action_and_bindings(InsertComplete(), ('M-RETURN',)) self.add_action_and_bindings(InsertComplete(), ('M-RETURN',))
self.add_action_and_bindings(InsertCancel(), ('C-]',)) self.add_action_and_bindings(InsertCancel(), ('C-]',))
self.add_action_and_bindings(InsertTab(), ('TAB',)) self.add_action_and_bindings(InsertTab(), ('TAB',))
for c in string.letters + string.digits + string.punctuation: for c in string.letters + string.digits + string.punctuation:
self.add_binding('insert-string-%s' % c, c) self.add_binding('insert-string-%s' % c, c)
def insert_line(w):
s = w.buffer.make_string()
w.mode.lines.append(s)
w.buffer.set_data('')
class InsertTab(method.Method): class InsertTab(method.Method):
def _execute(self, w, **vargs): def _execute(self, w, **vargs):
w.insert_string_at_cursor(' ' * w.mode.tabwidth) w.insert_string_at_cursor(' ' * w.mode.tabwidth)
class InsertLine(method.Method):
class InsertExec(method.Method):
def _execute(self, w, **vargs): def _execute(self, w, **vargs):
s = w.buffer.make_string() insert_line(w)
w.mode.lines.append(s)
w.buffer.set_data('')
w.mode.history[-1] = s
w.mode.history.append('')
w.mode.hindex = len(w.mode.history) - 1
class InsertComplete(method.Method): class InsertComplete(method.Method):
def execute(self, w, **vargs): def execute(self, w, **vargs):
s = '\n'.join(w.mode.lines) insert_line(w)
w.buffer.callback(s) w.buffer.callback('\n'.join(w.mode.lines))
w.application.close_mini_buffer() w.application.close_mini_buffer()
class InsertCancel(method.Method): class InsertCancel(method.Method):
def execute(self, w, **vargs): def execute(self, w, **vargs):
w.application.close_mini_buffer() w.application.close_mini_buffer()

View File

@ -1,5 +1,5 @@
import os.path, string import os.path, string
import highlight, regex import color, highlight, regex
from point import Point from point import Point
WORD_LETTERS = list(string.letters + string.digits) WORD_LETTERS = list(string.letters + string.digits)
@ -125,7 +125,7 @@ class Window(object):
l = 0 l = 0
x = min(self.cursor.x, l) x = min(self.cursor.x, l)
return Point(x, self.cursor.y) return Point(x, self.cursor.y)
# last visible point # last visible point
def _calc_last(self): def _calc_last(self):
(x, y) = self.first.xy() (x, y) = self.first.xy()
@ -151,7 +151,7 @@ class Window(object):
def set_size(self, width, height): def set_size(self, width, height):
assert type(width) == type(0), width assert type(width) == type(0), width
assert type(height) == type(0), height assert type(height) == type(0), height
self.width = width self.width = width - self.mode.lmargin - self.mode.rmargin
self.height = height self.height = height
self.redraw() self.redraw()