parent
c33b23f95b
commit
4614d4ee20
|
@ -478,6 +478,14 @@ class IperlBuffer(InterpreterBuffer):
|
|||
return ('iperl', '-p')
|
||||
def get_env(self):
|
||||
return {'PERL5LIB': self.application.config.get('perl.lib', '.')}
|
||||
def get_completions(self, x1, x2, line):
|
||||
self.pipe.stdin.write("COMPLETE:%d:%d:%s\n" % (x1, x2, line))
|
||||
self.pipe.stdin.flush()
|
||||
(typ_, value) = self.pipe_readline()
|
||||
assert typ_ == 'COMPLETIONS', '%r %r' % (typ_, value)
|
||||
candidates = [x for x in value.split('|') if x]
|
||||
self.pipe_read()
|
||||
return candidates
|
||||
|
||||
class IpythonBuffer(InterpreterBuffer):
|
||||
_basename = 'IPython'
|
||||
|
|
|
@ -83,41 +83,34 @@ class GetToken(Method):
|
|||
|
||||
class TokenComplete(Method):
|
||||
'''Complete token names based on other tokens in the buffer'''
|
||||
name_overrides = {}
|
||||
def _prune_candidates(self, t, minlen, candidates):
|
||||
if not candidates:
|
||||
return ([], t.string)
|
||||
i = len(t.string)
|
||||
while i < minlen:
|
||||
c = candidates[0][i]
|
||||
for s in candidates:
|
||||
if s[i] != c:
|
||||
return (candidates, candidates[0][:i])
|
||||
i += 1
|
||||
return (candidates, candidates[0][:minlen])
|
||||
def _min_completion(self, w, t):
|
||||
h = w.get_highlighter()
|
||||
minlen = None
|
||||
if t.name in self.name_overrides:
|
||||
ok = name_overrides[t.name]
|
||||
else:
|
||||
ok = (t.name,)
|
||||
|
||||
strings = {}
|
||||
candidates = {}
|
||||
for line in h.tokens:
|
||||
for t2 in line:
|
||||
if t2 is t:
|
||||
continue
|
||||
elif False and t2.name not in ok:
|
||||
elif False and t2.name != t.name:
|
||||
continue
|
||||
elif t2.string.startswith(t.string):
|
||||
strings[t2.string] = 1
|
||||
candidates[t2.string] = 1
|
||||
if minlen is None:
|
||||
minlen = len(t2.string)
|
||||
else:
|
||||
minlen = min(minlen, len(t2.string))
|
||||
|
||||
strings = strings.keys()
|
||||
if not strings:
|
||||
return ([], t.string)
|
||||
|
||||
i = len(t.string)
|
||||
while i < minlen:
|
||||
c = strings[0][i]
|
||||
for s in strings:
|
||||
if s[i] != c:
|
||||
return (strings, strings[0][:i])
|
||||
i += 1
|
||||
return (strings, strings[0][:minlen])
|
||||
return self._prune_candidates(t, minlen, candidates.keys())
|
||||
|
||||
def _execute(self, w, **vargs):
|
||||
t = w.get_token2()
|
||||
|
|
|
@ -190,7 +190,7 @@ class Fundamental(Handler):
|
|||
self.add_bindings('justify-left', ('C-c b',))
|
||||
self.add_bindings('indent-block', ('C-c >',))
|
||||
self.add_bindings('unindent-block', ('C-c <',))
|
||||
self.add_bindings('token-complete', ('M-c', 'C-c c', 'C-c TAB',))
|
||||
self.add_bindings('token-complete', ('C-x TAB',))
|
||||
self.add_bindings('open-aes-file', ('C-c a',))
|
||||
self.add_bindings('open-console', ('M-e',))
|
||||
self.add_bindings('show-bindings-buffer', ('C-c M-h',))
|
||||
|
|
|
@ -26,7 +26,7 @@ class IperlExec(method.Method):
|
|||
|
||||
b.pipe.stdin.write("ENTER:%s\n" % s)
|
||||
b.pipe.stdin.flush()
|
||||
output = w.mode._read()
|
||||
output = b.pipe_read()
|
||||
b.insert_string(b.get_buffer_end(), output, force=True)
|
||||
|
||||
class IperlTab(method.Method):
|
||||
|
@ -47,14 +47,7 @@ class IperlTab(method.Method):
|
|||
x1 -= 1
|
||||
word = line[x1:x2]
|
||||
|
||||
b.pipe.stdin.write("COMPLETE:%d:%d:%s\n" % (x1, x2, s))
|
||||
b.pipe.stdin.flush()
|
||||
(typ_, value) = w.mode._readline()
|
||||
assert typ_ == 'COMPLETIONS', '%r %r' % (typ_, value)
|
||||
|
||||
candidates = [x for x in value.split('|') if x]
|
||||
w.mode._read()
|
||||
|
||||
candidates = b.get_completions(x1, x2, s)
|
||||
if candidates:
|
||||
s = completer.find_common_string(candidates)
|
||||
w.buffer.delete(Point(x1, 0), Point(x2, 0), force=True)
|
||||
|
@ -63,7 +56,7 @@ class IperlTab(method.Method):
|
|||
|
||||
class IperlPathStart(method.Method):
|
||||
'''Interactively run perl statements in the context of a buffer'''
|
||||
def _start(self, w, parent):
|
||||
def _start(self, w, parent, switch=True):
|
||||
a = w.application
|
||||
if w.buffer.btype == 'iperl':
|
||||
b = w.buffer
|
||||
|
@ -76,17 +69,17 @@ class IperlPathStart(method.Method):
|
|||
else:
|
||||
b = a.get_buffer_by_name(name)
|
||||
self.main_buffer = b
|
||||
if a.window().buffer is not b:
|
||||
if switch and a.window().buffer is not b:
|
||||
a.switch_buffer(b)
|
||||
f = lambda x: None
|
||||
w.application.open_mini_buffer('*** ', f, self, None, 'iperlmini')
|
||||
def execute(self, w, **vargs):
|
||||
self._start(w, w.buffer)
|
||||
if switch:
|
||||
w.application.open_mini_buffer('*** ', lambda x: None, self, None, 'iperlmini')
|
||||
def execute(self, w, switch=True):
|
||||
self._start(w, w.buffer, switch)
|
||||
|
||||
class IperlStart(IperlPathStart):
|
||||
'''Interactively run perl statements'''
|
||||
def execute(self, w, **vargs):
|
||||
self._start(w, None)
|
||||
def execute(self, w, switch=True):
|
||||
self._start(w, None, switch=True)
|
||||
|
||||
class IperlPageUp(mode.consolemini.ConsolePageUp):
|
||||
subbuf = '*IPerl*'
|
||||
|
|
27
mode/perl.py
27
mode/perl.py
|
@ -1,5 +1,5 @@
|
|||
import os, re, sets, string, sys
|
||||
import color, commands, completer, context, default, method, mode, regex, tab
|
||||
import buffer, color, commands, completer, context, default, method, mode, regex, tab
|
||||
from point import Point
|
||||
from lex import Grammar, PatternRule, ContextPatternRule, RegionRule, OverridePatternRule, PatternGroupRule
|
||||
from method import Argument, Method, WrapParagraph
|
||||
|
@ -486,6 +486,27 @@ class PerlWrapParagraph(method.WrapParagraph):
|
|||
else:
|
||||
w.set_error("did not detect comment or pod lines")
|
||||
|
||||
class PerlSemanticComplete(method.introspect.TokenComplete):
|
||||
def _min_completion(self, w, t):
|
||||
a = w.application
|
||||
a.methods['iperl-path-start'].execute(w, switch=False)
|
||||
|
||||
name = buffer.IperlBuffer.create_name(w.buffer)
|
||||
b = a.get_buffer_by_name(name)
|
||||
|
||||
line = w.buffer.lines[t.y]
|
||||
(x1, x2) = (t.x, t.end_x())
|
||||
candidates = b.get_completions(x1, x2, line)
|
||||
|
||||
minlen = None
|
||||
for candidate in candidates:
|
||||
if minlen is None:
|
||||
minlen = len(candidate)
|
||||
else:
|
||||
minlen = min(minlen, len(candidate))
|
||||
|
||||
return self._prune_candidates(t, minlen, candidates)
|
||||
|
||||
class PerlOpenModule(method.Method):
|
||||
args = [Argument("module", type=type(""), prompt="Open Perl Module: ")]
|
||||
def _execute(self, w, **vargs):
|
||||
|
@ -670,7 +691,8 @@ class Perl(mode.Fundamental):
|
|||
actions = [PerlSetLib, PerlCheckSyntax, PerlHashCleanup,
|
||||
PerlViewModulePerldoc, PerlViewWordPerldoc, PerlWrapParagraph,
|
||||
PerlInitFunctions, PerlGotoFunction, PerlWhichFunction,
|
||||
PerlListFunctions, PerlOpenModule, PerlOpenModuleWord]
|
||||
PerlListFunctions, PerlOpenModule, PerlOpenModuleWord,
|
||||
PerlSemanticComplete]
|
||||
completers = {
|
||||
'perlfunction': PerlFunctionCompleter(),
|
||||
}
|
||||
|
@ -700,6 +722,7 @@ class Perl(mode.Fundamental):
|
|||
self.add_bindings('perl-goto-function', ('C-c M-g',))
|
||||
self.add_bindings('perl-open-module', ('C-c C-f',))
|
||||
self.add_bindings('perl-open-module-word', ('C-c M-f',))
|
||||
self.add_bindings('perl-semantic-complete', ('C-c TAB',))
|
||||
self.add_bindings('close-paren', (')'))
|
||||
self.add_bindings('close-bracket', (']'))
|
||||
self.add_bindings('close-brace', ('}'))
|
||||
|
|
Loading…
Reference in New Issue