Show where snippets are defined in selection.

Fixes #184.
This commit is contained in:
Holger Rapp 2014-03-22 20:20:56 +01:00
parent 7c34a3400b
commit 360f58dbf6
6 changed files with 31 additions and 21 deletions

View File

@ -39,7 +39,7 @@ class SnippetDefinition(object):
_TABS = re.compile(r"^\t*") _TABS = re.compile(r"^\t*")
def __init__(self, priority, trigger, value, description, def __init__(self, priority, trigger, value, description,
options, globals): options, globals, location):
self._priority = priority self._priority = priority
self._trigger = as_unicode(trigger) self._trigger = as_unicode(trigger)
self._value = as_unicode(value) self._value = as_unicode(value)
@ -48,6 +48,7 @@ class SnippetDefinition(object):
self._matched = "" self._matched = ""
self._last_re = None self._last_re = None
self._globals = globals self._globals = globals
self._location = location
# Make sure that we actually match our trigger in case we are # Make sure that we actually match our trigger in case we are
# immediately expanded. # immediately expanded.
@ -97,6 +98,11 @@ class SnippetDefinition(object):
could_match().""" could_match()."""
return self._matched return self._matched
@property
def location(self):
"""Where this snippet was defined."""
return self._location
def matches(self, trigger): def matches(self, trigger):
"""Returns True if this snippet matches 'trigger'.""" """Returns True if this snippet matches 'trigger'."""
# If user supplies both "w" and "i", it should perhaps be an # If user supplies both "w" and "i", it should perhaps be an

View File

@ -11,9 +11,9 @@ class SnipMateSnippetDefinition(SnippetDefinition):
SNIPMATE_SNIPPET_PRIORITY = -1000 SNIPMATE_SNIPPET_PRIORITY = -1000
def __init__(self, trigger, value, description): def __init__(self, trigger, value, description, location):
SnippetDefinition.__init__(self, self.SNIPMATE_SNIPPET_PRIORITY, SnippetDefinition.__init__(self, self.SNIPMATE_SNIPPET_PRIORITY,
trigger, value, description, "", {}) trigger, value, description, "", {}, location)
def instantiate(self, snippet_instance, initial_text, indent): def instantiate(self, snippet_instance, initial_text, indent):
parse_and_instantiate(snippet_instance, initial_text, indent) parse_and_instantiate(snippet_instance, initial_text, indent)

View File

@ -49,9 +49,9 @@ def snipmate_files_for(ft):
ret.add(fn) ret.add(fn)
return ret return ret
def _parse_snippet_file(content, filename): def _parse_snippet_file(content, full_filename):
"""Parses 'content' assuming it is a .snippet file and yields events.""" """Parses 'content' assuming it is a .snippet file and yields events."""
filename = filename[:-len(".snippet")] # strip extension filename = full_filename[:-len(".snippet")] # strip extension
segments = _splitall(filename) segments = _splitall(filename)
segments = segments[segments.index("snippets")+1:] segments = segments[segments.index("snippets")+1:]
assert len(segments) in (2, 3) assert len(segments) in (2, 3)
@ -62,10 +62,12 @@ def _parse_snippet_file(content, filename):
# Chomp \n if any. # Chomp \n if any.
if content and content.endswith(os.linesep): if content and content.endswith(os.linesep):
content = content[:-len(os.linesep)] content = content[:-len(os.linesep)]
yield "snippet", (SnipMateSnippetDefinition(trigger, content, description),) yield "snippet", (SnipMateSnippetDefinition(trigger, content,
description, full_filename),)
def _parse_snippet(line, lines): def _parse_snippet(line, lines, filename):
"""Parse a snippet defintions.""" """Parse a snippet defintions."""
start_line_index = lines.line_index
trigger, description = head_tail(line[len("snippet"):].lstrip()) trigger, description = head_tail(line[len("snippet"):].lstrip())
content = "" content = ""
while True: while True:
@ -80,9 +82,9 @@ def _parse_snippet(line, lines):
content += line content += line
content = content[:-1] # Chomp the last newline content = content[:-1] # Chomp the last newline
return "snippet", (SnipMateSnippetDefinition( return "snippet", (SnipMateSnippetDefinition(
trigger, content, description),) trigger, content, description, "%s:%i" % (filename, start_line_index)),)
def _parse_snippets_file(data): def _parse_snippets_file(data, filename):
"""Parse 'data' assuming it is a .snippets file. Yields events in the """Parse 'data' assuming it is a .snippets file. Yields events in the
file.""" file."""
lines = LineIterator(data) lines = LineIterator(data)
@ -94,7 +96,7 @@ def _parse_snippets_file(data):
if head == "extends": if head == "extends":
yield handle_extends(tail, lines.line_index) yield handle_extends(tail, lines.line_index)
elif head in "snippet": elif head in "snippet":
snippet = _parse_snippet(line, lines) snippet = _parse_snippet(line, lines, filename)
if snippet is not None: if snippet is not None:
yield snippet yield snippet
elif head and not head.startswith('#'): elif head and not head.startswith('#'):
@ -110,5 +112,5 @@ class SnipMateFileSource(SnippetFileSource):
for event, data in _parse_snippet_file(filedata, filename): for event, data in _parse_snippet_file(filedata, filename):
yield event, data yield event, data
else: else:
for event, data in _parse_snippets_file(filedata): for event, data in _parse_snippets_file(filedata, filename):
yield event, data yield event, data

View File

@ -47,8 +47,9 @@ def find_all_snippet_files(ft):
ret.add(fn) ret.add(fn)
return ret return ret
def _handle_snippet_or_global(line, lines, python_globals, priority): def _handle_snippet_or_global(filename, line, lines, python_globals, priority):
"""Parses the snippet that begins at the current line.""" """Parses the snippet that begins at the current line."""
start_line_index = lines.line_index
descr = "" descr = ""
opts = "" opts = ""
@ -96,11 +97,12 @@ def _handle_snippet_or_global(line, lines, python_globals, priority):
python_globals[trig].append(content) python_globals[trig].append(content)
elif snip == "snippet": elif snip == "snippet":
return "snippet", (UltiSnipsSnippetDefinition(priority, trig, content, return "snippet", (UltiSnipsSnippetDefinition(priority, trig, content,
descr, opts, python_globals),) descr, opts, python_globals,
"%s:%i" % (filename, start_line_index)),)
else: else:
return "error", ("Invalid snippet type: '%s'" % snip, lines.line_index) return "error", ("Invalid snippet type: '%s'" % snip, lines.line_index)
def _parse_snippets_file(data): def _parse_snippets_file(data, filename):
"""Parse 'data' assuming it is a snippet file. Yields events in the """Parse 'data' assuming it is a snippet file. Yields events in the
file.""" file."""
@ -113,7 +115,7 @@ def _parse_snippets_file(data):
head, tail = head_tail(line) head, tail = head_tail(line)
if head in ("snippet", "global"): if head in ("snippet", "global"):
snippet = _handle_snippet_or_global(line, lines, snippet = _handle_snippet_or_global(filename, line, lines,
python_globals, current_priority) python_globals, current_priority)
if snippet is not None: if snippet is not None:
yield snippet yield snippet
@ -136,5 +138,5 @@ class UltiSnipsFileSource(SnippetFileSource):
return find_all_snippet_files(ft) return find_all_snippet_files(ft)
def _parse_snippet_file(self, filedata, filename): def _parse_snippet_file(self, filedata, filename):
for event, data in _parse_snippets_file(filedata): for event, data in _parse_snippets_file(filedata, filename):
yield event, data yield event, data

View File

@ -41,8 +41,8 @@ def _ask_snippets(snippets):
""" Given a list of snippets, ask the user which one they """ Given a list of snippets, ask the user which one they
want to use, and return it. want to use, and return it.
""" """
display = [as_unicode("%i: %s") % (i+1, escape(s.description, '\\')) for display = [as_unicode("%i: %s (%s)") % (i+1, escape(s.description, '\\'),
i, s in enumerate(snippets)] s.location) for i, s in enumerate(snippets)]
return _ask_user(snippets, display) return _ask_user(snippets, display)
def err_to_scratch_buffer(func): def err_to_scratch_buffer(func):
@ -193,14 +193,14 @@ class SnippetManager(object):
"""Add a snippet to the list of known snippets of the given 'ft'.""" """Add a snippet to the list of known snippets of the given 'ft'."""
self._added_snippets_source.add_snippet(ft, self._added_snippets_source.add_snippet(ft,
UltiSnipsSnippetDefinition(priority, trigger, value, UltiSnipsSnippetDefinition(priority, trigger, value,
description, options, {})) description, options, {}, "added"))
@err_to_scratch_buffer @err_to_scratch_buffer
def expand_anon(self, value, trigger="", description="", options=""): def expand_anon(self, value, trigger="", description="", options=""):
"""Expand an anonymous snippet right here.""" """Expand an anonymous snippet right here."""
before = _vim.buf.line_till_cursor before = _vim.buf.line_till_cursor
snip = UltiSnipsSnippetDefinition(0, trigger, value, description, snip = UltiSnipsSnippetDefinition(0, trigger, value, description,
options, {}) options, {}, "")
if not trigger or snip.matches(before): if not trigger or snip.matches(before):
self._do_snippet(snip, before) self._do_snippet(snip, before)

View File

@ -3343,7 +3343,7 @@ class MySnippetSource(SnippetSource):
if before.endswith('blumba'): if before.endswith('blumba'):
return [ return [
UltiSnipsSnippetDefinition( UltiSnipsSnippetDefinition(
-100, "blumba", "this is a dynamic snippet", "", "", {}) -100, "blumba", "this is a dynamic snippet", "", "", {}, "blub")
] ]
return [] return []
""") """)