add support for explicit insert mode completion using C-x prefix

This commit is contained in:
Maxime Coste 2013-08-04 19:34:08 +02:00
parent 0f4cecfa3e
commit c05f9f31dd
2 changed files with 33 additions and 11 deletions

View File

@ -380,6 +380,18 @@ Some options are built in kakoune, and can be used to control it's behaviour:
* +insert_hide_sel+ _bool_: hide the selection (except the last * +insert_hide_sel+ _bool_: hide the selection (except the last
element) in insert mode element) in insert mode
Insert mode completion
----------------------
Kakoune can propose completions while inserting text, the +completers+ option
control automatic completion, which kicks in when a certain idle timeout is
reached (100 milliseconds). Insert mode completion can be explicitely triggered
using *control-x*, followed, by:
* *f* : filename completion
* *w* : buffer word completion
* *o* : option based completion
Highlighters Highlighters
------------ ------------

View File

@ -689,7 +689,7 @@ public:
return { begin.coord(), pos.coord(), std::move(res), buffer.timestamp() }; return { begin.coord(), pos.coord(), std::move(res), buffer.timestamp() };
} }
BufferCompletion complete_opt(const Buffer& buffer, BufferCoord cursor_pos) BufferCompletion complete_option(const Buffer& buffer, BufferCoord cursor_pos)
{ {
const StringList& opt = options()["completions"].get<StringList>(); const StringList& opt = options()["completions"].get<StringList>();
if (opt.empty()) if (opt.empty())
@ -748,7 +748,7 @@ private:
if (not m_completions.is_valid()) if (not m_completions.is_valid())
{ {
auto& completers = options()["completers"].get<StringList>(); auto& completers = options()["completers"].get<StringList>();
if (contains(completers, "option") and try_complete<&BufferCompleter::complete_opt>()) if (contains(completers, "option") and try_complete<&BufferCompleter::complete_option>())
return true; return true;
if (contains(completers, "word=buffer") and try_complete<&BufferCompleter::complete_word<false>>()) if (contains(completers, "word=buffer") and try_complete<&BufferCompleter::complete_word<false>>())
return true; return true;
@ -792,13 +792,25 @@ public:
return reset_normal_mode().on_key(key); return reset_normal_mode().on_key(key);
last_insert().second.push_back(key); last_insert().second.push_back(key);
if (m_insert_reg) if (m_mode == Mode::InsertReg)
{ {
if (key.modifiers == Key::Modifiers::None) if (key.modifiers == Key::Modifiers::None)
m_inserter.insert(RegisterManager::instance()[key.key].values(context())); m_inserter.insert(RegisterManager::instance()[key.key].values(context()));
m_insert_reg = false; m_mode = Mode::Default;
return; return;
} }
if (m_mode == Mode::Complete)
{
if (key.key == 'f')
m_completer.try_complete<&BufferCompleter::complete_filename>();
if (key.key == 'w')
m_completer.try_complete<&BufferCompleter::complete_word<true>>();
if (key.key == 'o')
m_completer.try_complete<&BufferCompleter::complete_option>();
m_mode = Mode::Default;
return;
}
bool update_completions = true; bool update_completions = true;
bool moved = false; bool moved = false;
if (key == Key::Escape or key == Key{ Key::Modifiers::Control, 'c' }) if (key == Key::Escape or key == Key{ Key::Modifiers::Control, 'c' })
@ -835,7 +847,7 @@ public:
context().hooks().run_hook("InsertKey", key_to_str(key), context()); context().hooks().run_hook("InsertKey", key_to_str(key), context());
} }
else if (key == Key{ Key::Modifiers::Control, 'r' }) else if (key == Key{ Key::Modifiers::Control, 'r' })
m_insert_reg = true; m_mode = Mode::InsertReg;
else if ( key == Key{ Key::Modifiers::Control, 'm' }) else if ( key == Key{ Key::Modifiers::Control, 'm' })
m_inserter.insert(String() + '\n'); m_inserter.insert(String() + '\n');
else if ( key == Key{ Key::Modifiers::Control, 'i' }) else if ( key == Key{ Key::Modifiers::Control, 'i' })
@ -850,11 +862,8 @@ public:
m_completer.select(-1); m_completer.select(-1);
update_completions = false; update_completions = false;
} }
else if ( key == Key{ Key::Modifiers::Control, 'f' }) else if ( key == Key{ Key::Modifiers::Control, 'x' })
{ m_mode = Mode::Complete;
m_completer.try_complete<&BufferCompleter::complete_filename>();
update_completions = false;
}
if (update_completions) if (update_completions)
m_idle_timer.set_next_date(Clock::now() + idle_timeout); m_idle_timer.set_next_date(Clock::now() + idle_timeout);
@ -862,7 +871,8 @@ public:
context().hooks().run_hook("InsertMove", key_to_str(key), context()); context().hooks().run_hook("InsertMove", key_to_str(key), context());
} }
private: private:
bool m_insert_reg = false; enum class Mode { Default, Complete, InsertReg };
Mode m_mode = Mode::Default;
IncrementalInserter m_inserter; IncrementalInserter m_inserter;
BufferCompleter m_completer; BufferCompleter m_completer;
Timer m_idle_timer; Timer m_idle_timer;