[gedit-plugins] Added new 'align' module
- From: Jesse van den Kieboom <jessevdk src gnome org>
- To: commits-list gnome org
- Cc:
- Subject: [gedit-plugins] Added new 'align' module
- Date: Sun, 14 Mar 2010 23:46:52 +0000 (UTC)
commit 02ba892dcd516aebbff0490521d7b2a17e16b1d6
Author: Jesse van den Kieboom <jesse icecrew nl>
Date: Mon Mar 15 00:46:36 2010 +0100
Added new 'align' module
This module aligns lines of text on columns separated by whitespace. Additionally, a powerful regular expression align
function allows to align columns on specific regular expressions
and specific groups within that regular expression
plugins/commander/modules/Makefile.am | 1 +
plugins/commander/modules/align.py | 189 +++++++++++++++++++++++++++++++++
2 files changed, 190 insertions(+), 0 deletions(-)
---
diff --git a/plugins/commander/modules/Makefile.am b/plugins/commander/modules/Makefile.am
index fd847ce..fd55ecf 100644
--- a/plugins/commander/modules/Makefile.am
+++ b/plugins/commander/modules/Makefile.am
@@ -5,6 +5,7 @@ SUBDIRS = find
plugindir = $(GEDIT_PLUGINS_DATA_DIR)/commander/modules
plugin_PYTHON = \
+ align.py
bookmark.py \
doc.py \
edit.py \
diff --git a/plugins/commander/modules/align.py b/plugins/commander/modules/align.py
new file mode 100644
index 0000000..3ca65d5
--- /dev/null
+++ b/plugins/commander/modules/align.py
@@ -0,0 +1,189 @@
+import commander.commands as commands
+import commander.commands.completion
+import commander.commands.result
+import commander.commands.exceptions
+
+import re
+
+__commander_module__ = True
+
+class Line:
+ def __init__(self, line, reg, tabwidth):
+ self.tabwidth = tabwidth
+ self.line = line
+ self.matches = list(reg.finditer(line))
+
+ if not self.matches:
+ self.newline = str(line)
+ else:
+ self.newline = line[0:self.matches[0].start(0)]
+
+ def matches_len(self):
+ return len(self.matches)
+
+ def new_len(self, extra=''):
+ return len((self.newline + extra).expandtabs(self.tabwidth))
+
+ def match(self, idx):
+ if idx >= self.matches_len():
+ return None
+
+ return self.matches[idx]
+
+ def append(self, idx, num, group):
+ m = self.match(idx)
+
+ if m == None:
+ return
+
+ if len(m.groups()) <= group - 1:
+ gidx = 0
+ else:
+ gidx = group
+
+ # First append leading match
+ self.newline += self.line[m.start(0):m.start(gidx)]
+
+ # Then do the indent
+ self.newline += ' ' * (num - self.new_len())
+
+ t = m.group(gidx)
+
+ # Then append the rest of the match
+ mnext = self.match(idx + 1)
+
+ if mnext == None:
+ endidx = None
+ else:
+ endidx = mnext.start(0)
+
+ self.newline += t.lstrip() + self.line[m.end(gidx):endidx]
+
+ def __str__(self):
+ return self.newline
+
+def __default__(view):
+ """Align selected text in columns: align
+
+Align the selected text in columns separated by white space (spaces and tabs)"""
+ yield regex(view, '\s+')
+
+def _find_max_align(lines, idx, group):
+ num = 0
+ spaces = re.compile('^\s*')
+
+ for line in lines:
+ m = line.match(idx)
+
+ if m != None:
+ if len(m.groups()) <= group - 1:
+ gidx = 0
+ else:
+ gidx = group
+
+ g = m.group(gidx)
+ until = m.start(gidx) - m.start(0)
+
+ # Measure where to align it
+ l = line.new_len(m.group(0)[0:until])
+ else:
+ l = line.new_len()
+
+ if l > num:
+ num = l
+
+ return num
+
+def _regex(view, reg, group, additional_ws, flags=0):
+ buf = view.get_buffer()
+
+ bounds = buf.get_selection_bounds()
+
+ if not bounds or (bounds[1].get_line() - bounds[0].get_line() == 0):
+ raise commander.commands.exceptions.Execute('You need to select a number of lines to align')
+
+ if reg == None:
+ reg, words, modifier = (yield commander.commands.result.Prompt('Regex:'))
+
+ try:
+ reg = re.compile(reg, flags)
+ except Exception, e:
+ raise commander.commands.exceptions.Execute('Failed to compile regular expression: %s' % (e,))
+
+ if group == None:
+ group, words, modifier = (yield commander.commands.result.Prompt('Group (1):'))
+
+ try:
+ group = int(group)
+ except:
+ group = 1
+
+ if additional_ws == None:
+ additional_ws, words, modifier = (yield commander.commands.result.Prompt('Additional Whitespace (0):'))
+
+ try:
+ additional_ws = int(additional_ws)
+ except:
+ additional_ws = 0
+
+ start, end = bounds
+
+ if not start.starts_line():
+ start.set_line_offset(0)
+
+ if not end.ends_line():
+ end.forward_to_line_end()
+
+ lines = start.get_text(end).splitlines()
+ newlines = []
+ num = 0
+ tabwidth = view.get_tab_width()
+
+ for line in lines:
+ ln = Line(line, reg, tabwidth)
+ newlines.append(ln)
+
+ if len(ln.matches) > num:
+ num = len(ln.matches)
+
+ for i in range(num):
+ al = _find_max_align(newlines, i, group)
+
+ for line in newlines:
+ line.append(i, al + 1 + additional_ws, group)
+
+ # Replace lines
+ aligned = '\n'.join([str(x) for x in newlines])
+
+ buf.begin_user_action()
+ buf.delete(bounds[0], bounds[1])
+ buf.insert(bounds[1], aligned)
+ buf.end_user_action()
+
+ yield commander.commands.result.DONE
+
+def regex(view, reg=None, group=1, additional_ws=0):
+ """Align selected in columns using a regular expression: align.regex [<regex>] [<group>] [<ws>]
+
+Align the selected text in columns separated by the specified regular expression.
+The optional group argument specifies on which group in the regular expression
+the text should be aligned. Additional whitespace will be added in front of
+the matched group to align each column. The optional <ws> argument can
+be used to add additional whitespace to the column separation.
+
+The regular expression will be matched in case-sensitive mode"""
+
+ yield _regex(view, reg, group, additional_ws)
+
+def regex_i(view, reg=None, group=1, additional_ws=0):
+ """Align selected in columns using a regular expression: align.regex [<regex>] [<group>] [<ws>]
+
+Align the selected text in columns separated by the specified regular expression.
+The optional group argument specifies on which group in the regular expression
+the text should be aligned. Additional whitespace will be added in front of
+the matched group to align each column. The optional <ws> argument can
+be used to add additional whitespace to the column separation.
+
+The regular expression will be matched in case-insensitive mode"""
+
+ yield _regex(view, reg, group, additional_ws, re.IGNORECASE)
[
Date Prev][
Date Next] [
Thread Prev][
Thread Next]
[
Thread Index]
[
Date Index]
[
Author Index]