aboutsummaryrefslogtreecommitdiff
diff options
context:
space:
mode:
authormitchell <70453897+667e-11@users.noreply.github.com>2016-04-05 20:49:54 -0400
committermitchell <70453897+667e-11@users.noreply.github.com>2016-04-05 20:49:54 -0400
commit4b0e565061d8e0b292966cbc5935e9abb410ebab (patch)
tree1f4eac10e70768d269dbbbed54a3edbc982c2e5a
parent47d8b1a2beba8a737c325fcfe95050f399fdeaf9 (diff)
downloadtextadept-4b0e565061d8e0b292966cbc5935e9abb410ebab.tar.gz
textadept-4b0e565061d8e0b292966cbc5935e9abb410ebab.zip
Improved efficiency of word autocompletion from all buffers.
Also fixed a bug that reset some non-focused buffer properties.
-rw-r--r--modules/textadept/editing.lua35
-rw-r--r--src/textadept.c5
2 files changed, 19 insertions, 21 deletions
diff --git a/modules/textadept/editing.lua b/modules/textadept/editing.lua
index 00f8edcb..2f6062b7 100644
--- a/modules/textadept/editing.lua
+++ b/modules/textadept/editing.lua
@@ -552,28 +552,25 @@ end
-- @see buffer.word_chars
-- @see autocomplete
M.autocompleters.word = function()
- local list, ignore_case = {}, buffer.auto_c_ignore_case
- local line, pos = buffer:get_cur_line()
- local word_char = '['..buffer.word_chars:gsub('(%p)', '%%%1')..']'
- local word = line:sub(1, pos):match(word_char..'*$')
- if word == '' then return nil end
- local word_patt = word:gsub('(%p)', '%%%1')
- if ignore_case then
- word_patt = word_patt:lower():gsub('%l', function(c)
- return string.format('[%s%s]', string.upper(c), c)
- end)
- end
- word_patt = '()('..word_patt..word_char..'+)'
- local nonword_char = '^[^'..buffer.word_chars:gsub('(%p)', '%%%1')..']'
+ local list, matches = {}, {}
+ local s = buffer:word_start_position(buffer.current_pos, true)
+ if s == buffer.current_pos then return end
+ local word = buffer:text_range(s, buffer.current_pos)
for i = 1, #_BUFFERS do
if _BUFFERS[i] == buffer or M.AUTOCOMPLETE_ALL then
- local text = _BUFFERS[i]:get_text()
- for match_pos, match in text:gmatch(word_patt) do
- -- Frontier pattern (%f) is too slow, so check prior char after a match.
- if (match_pos == 1 or text:find(nonword_char, match_pos - 1)) and
- not list[match] then
- list[#list + 1], list[match] = match, true
+ local buffer = _BUFFERS[i]
+ buffer.search_flags = buffer.FIND_WORDSTART
+ if not buffer.auto_c_ignore_case then
+ buffer.search_flags = buffer.search_flags + buffer.FIND_MATCHCASE
+ end
+ buffer:target_whole_document()
+ while buffer:search_in_target(word) > -1 do
+ local e = buffer:word_end_position(buffer.target_end, true)
+ local match = buffer:text_range(buffer.target_start, e)
+ if #match > #word and not matches[match] then
+ list[#list + 1], matches[match] = match, true
end
+ buffer:set_target_range(e, buffer.length)
end
end
end
diff --git a/src/textadept.c b/src/textadept.c
index a5daadda..fcd5da62 100644
--- a/src/textadept.c
+++ b/src/textadept.c
@@ -963,8 +963,8 @@ static sptr_t l_todoc(lua_State *L, int index) {
* returns 0 if they are equivalent, less than zero if that document belongs to
* the command entry, and greater than zero otherwise.
* In the last case, loads the document in `dummy_view` for non-global document
- * use. Raises and error if the value is not a Scintilla document or if the
- * document no longer exists.
+ * use (unless it is already loaded). Raises and error if the value is not a
+ * Scintilla document or if the document no longer exists.
* @param L The Lua state.
* @param index The stack index of the Scintilla document.
* @return 0, -1, or the Scintilla document's pointer
@@ -981,6 +981,7 @@ static sptr_t l_globaldoccompare(lua_State *L, int index) {
index, "this Buffer does not exist");
lua_pop(L, 2); // buffer, ta_buffers
if (doc == SS(command_entry, SCI_GETDOCPOINTER, 0, 0)) return -1;
+ if (doc == SS(dummy_view, SCI_GETDOCPOINTER, 0, 0)) return doc; // keep
return (SS(dummy_view, SCI_SETDOCPOINTER, 0, doc), doc);
} else return 0;
}