Selection: refactoring, move CaptureList to Selection
This commit is contained in:
parent
956ac60d4a
commit
b764a0a63e
|
@ -99,7 +99,7 @@ struct Context
|
||||||
|
|
||||||
void push_jump()
|
void push_jump()
|
||||||
{
|
{
|
||||||
const SelectionAndCaptures& jump = editor().selections().back();
|
const Selection& jump = editor().selections().back();
|
||||||
if (m_current_jump != m_jump_list.end())
|
if (m_current_jump != m_jump_list.end())
|
||||||
{
|
{
|
||||||
auto begin = m_current_jump;
|
auto begin = m_current_jump;
|
||||||
|
@ -115,7 +115,7 @@ struct Context
|
||||||
m_current_jump = m_jump_list.end();
|
m_current_jump = m_jump_list.end();
|
||||||
}
|
}
|
||||||
|
|
||||||
SelectionAndCaptures jump_forward()
|
Selection jump_forward()
|
||||||
{
|
{
|
||||||
if (m_current_jump != m_jump_list.end() and
|
if (m_current_jump != m_jump_list.end() and
|
||||||
m_current_jump + 1 != m_jump_list.end())
|
m_current_jump + 1 != m_jump_list.end())
|
||||||
|
@ -123,7 +123,7 @@ struct Context
|
||||||
throw runtime_error("no next jump");
|
throw runtime_error("no next jump");
|
||||||
}
|
}
|
||||||
|
|
||||||
SelectionAndCaptures jump_backward()
|
Selection jump_backward()
|
||||||
{
|
{
|
||||||
if (m_current_jump != m_jump_list.begin())
|
if (m_current_jump != m_jump_list.begin())
|
||||||
{
|
{
|
||||||
|
@ -164,8 +164,8 @@ private:
|
||||||
Insertion m_last_insert = {InsertMode::Insert, {}};
|
Insertion m_last_insert = {InsertMode::Insert, {}};
|
||||||
int m_numeric_param = 0;
|
int m_numeric_param = 0;
|
||||||
|
|
||||||
SelectionAndCapturesList m_jump_list;
|
SelectionList m_jump_list;
|
||||||
SelectionAndCapturesList::iterator m_current_jump = m_jump_list.begin();
|
SelectionList::iterator m_current_jump = m_jump_list.begin();
|
||||||
};
|
};
|
||||||
|
|
||||||
}
|
}
|
||||||
|
|
|
@ -25,7 +25,7 @@ void Editor::erase()
|
||||||
for (auto& sel : m_selections)
|
for (auto& sel : m_selections)
|
||||||
{
|
{
|
||||||
m_buffer->erase(sel.begin(), sel.end());
|
m_buffer->erase(sel.begin(), sel.end());
|
||||||
sel.selection.avoid_eol();
|
sel.avoid_eol();
|
||||||
}
|
}
|
||||||
}
|
}
|
||||||
|
|
||||||
|
@ -81,9 +81,9 @@ void Editor::insert(const String& string, InsertMode mode)
|
||||||
|
|
||||||
for (auto& sel : m_selections)
|
for (auto& sel : m_selections)
|
||||||
{
|
{
|
||||||
BufferIterator pos = prepare_insert(*m_buffer, sel.selection, mode);
|
BufferIterator pos = prepare_insert(*m_buffer, sel, mode);
|
||||||
m_buffer->insert(pos, string);
|
m_buffer->insert(pos, string);
|
||||||
sel.selection.avoid_eol();
|
sel.avoid_eol();
|
||||||
}
|
}
|
||||||
}
|
}
|
||||||
|
|
||||||
|
@ -101,7 +101,7 @@ void Editor::insert(const memoryview<String>& strings, InsertMode mode)
|
||||||
|
|
||||||
for (size_t i = 0; i < selections().size(); ++i)
|
for (size_t i = 0; i < selections().size(); ++i)
|
||||||
{
|
{
|
||||||
Selection& sel = m_selections[i].selection;
|
Selection& sel = m_selections[i];
|
||||||
BufferIterator pos = prepare_insert(*m_buffer, sel, mode);
|
BufferIterator pos = prepare_insert(*m_buffer, sel, mode);
|
||||||
size_t index = std::min(i, strings.size()-1);
|
size_t index = std::min(i, strings.size()-1);
|
||||||
m_buffer->insert(pos, strings[index]);
|
m_buffer->insert(pos, strings[index]);
|
||||||
|
@ -118,7 +118,7 @@ std::vector<String> Editor::selections_content() const
|
||||||
return contents;
|
return contents;
|
||||||
}
|
}
|
||||||
|
|
||||||
static void merge_overlapping(SelectionAndCapturesList& selections)
|
static void merge_overlapping(SelectionList& selections)
|
||||||
{
|
{
|
||||||
for (size_t i = 0; i < selections.size(); ++i)
|
for (size_t i = 0; i < selections.size(); ++i)
|
||||||
{
|
{
|
||||||
|
@ -126,7 +126,7 @@ static void merge_overlapping(SelectionAndCapturesList& selections)
|
||||||
{
|
{
|
||||||
if (overlaps(selections[i], selections[j]))
|
if (overlaps(selections[i], selections[j]))
|
||||||
{
|
{
|
||||||
selections[i].selection.merge_with(selections[j].selection);
|
selections[i].merge_with(selections[j]);
|
||||||
selections.erase(selections.begin() + j);
|
selections.erase(selections.begin() + j);
|
||||||
}
|
}
|
||||||
else
|
else
|
||||||
|
@ -144,8 +144,8 @@ void Editor::move_selections(CharCount offset, SelectMode mode)
|
||||||
auto limit = offset < 0 ? buffer().iterator_at_line_begin(last)
|
auto limit = offset < 0 ? buffer().iterator_at_line_begin(last)
|
||||||
: utf8::previous(buffer().iterator_at_line_end(last));
|
: utf8::previous(buffer().iterator_at_line_end(last));
|
||||||
last = utf8::advance(last, limit, offset);
|
last = utf8::advance(last, limit, offset);
|
||||||
sel.selection = Selection(mode == SelectMode::Extend ? sel.first() : last, last);
|
sel = Selection(mode == SelectMode::Extend ? sel.first() : last, last);
|
||||||
sel.selection.avoid_eol();
|
sel.avoid_eol();
|
||||||
}
|
}
|
||||||
merge_overlapping(m_selections);
|
merge_overlapping(m_selections);
|
||||||
}
|
}
|
||||||
|
@ -158,8 +158,8 @@ void Editor::move_selections(LineCount offset, SelectMode mode)
|
||||||
BufferCoord pos = sel.last().coord();
|
BufferCoord pos = sel.last().coord();
|
||||||
pos.line += offset;
|
pos.line += offset;
|
||||||
BufferIterator last = utf8::finish(m_buffer->iterator_at(pos, true));
|
BufferIterator last = utf8::finish(m_buffer->iterator_at(pos, true));
|
||||||
sel.selection = Selection(mode == SelectMode::Extend ? sel.first() : last, last);
|
sel = Selection(mode == SelectMode::Extend ? sel.first() : last, last);
|
||||||
sel.selection.avoid_eol();
|
sel.avoid_eol();
|
||||||
}
|
}
|
||||||
merge_overlapping(m_selections);
|
merge_overlapping(m_selections);
|
||||||
}
|
}
|
||||||
|
@ -181,7 +181,7 @@ void Editor::flip_selections()
|
||||||
{
|
{
|
||||||
check_invariant();
|
check_invariant();
|
||||||
for (auto& sel : m_selections)
|
for (auto& sel : m_selections)
|
||||||
std::swap(sel.selection.first(), sel.selection.last());
|
std::swap(sel.first(), sel.last());
|
||||||
}
|
}
|
||||||
|
|
||||||
void Editor::keep_selection(int index)
|
void Editor::keep_selection(int index)
|
||||||
|
@ -190,7 +190,7 @@ void Editor::keep_selection(int index)
|
||||||
|
|
||||||
if (index < m_selections.size())
|
if (index < m_selections.size())
|
||||||
{
|
{
|
||||||
SelectionAndCaptures sel = std::move(m_selections[index]);
|
Selection sel = std::move(m_selections[index]);
|
||||||
m_selections.clear();
|
m_selections.clear();
|
||||||
m_selections.push_back(std::move(sel));
|
m_selections.push_back(std::move(sel));
|
||||||
}
|
}
|
||||||
|
@ -210,7 +210,7 @@ void Editor::select(const BufferIterator& iterator)
|
||||||
m_selections.push_back(Selection(iterator, iterator));
|
m_selections.push_back(Selection(iterator, iterator));
|
||||||
}
|
}
|
||||||
|
|
||||||
void Editor::select(SelectionAndCapturesList selections)
|
void Editor::select(SelectionList selections)
|
||||||
{
|
{
|
||||||
if (selections.empty())
|
if (selections.empty())
|
||||||
throw runtime_error("no selections");
|
throw runtime_error("no selections");
|
||||||
|
@ -224,23 +224,23 @@ void Editor::select(const Selector& selector, SelectMode mode)
|
||||||
if (mode == SelectMode::Append)
|
if (mode == SelectMode::Append)
|
||||||
{
|
{
|
||||||
auto& sel = m_selections.back();
|
auto& sel = m_selections.back();
|
||||||
SelectionAndCaptures res = selector(sel.selection);
|
Selection res = selector(sel);
|
||||||
if (res.captures.empty())
|
if (res.captures().empty())
|
||||||
res.captures = sel.captures;
|
res.captures() = sel.captures();
|
||||||
m_selections.push_back(res);
|
m_selections.push_back(res);
|
||||||
}
|
}
|
||||||
else
|
else
|
||||||
{
|
{
|
||||||
for (auto& sel : m_selections)
|
for (auto& sel : m_selections)
|
||||||
{
|
{
|
||||||
SelectionAndCaptures res = selector(sel.selection);
|
Selection res = selector(sel);
|
||||||
if (mode == SelectMode::Extend)
|
if (mode == SelectMode::Extend)
|
||||||
sel.selection.merge_with(res.selection);
|
sel.merge_with(res);
|
||||||
else
|
else
|
||||||
sel.selection = std::move(res.selection);
|
sel = std::move(res);
|
||||||
|
|
||||||
if (not res.captures.empty())
|
if (not res.captures().empty())
|
||||||
sel.captures = std::move(res.captures);
|
sel.captures() = std::move(res.captures());
|
||||||
}
|
}
|
||||||
}
|
}
|
||||||
merge_overlapping(m_selections);
|
merge_overlapping(m_selections);
|
||||||
|
@ -255,17 +255,18 @@ void Editor::multi_select(const MultiSelector& selector)
|
||||||
{
|
{
|
||||||
check_invariant();
|
check_invariant();
|
||||||
|
|
||||||
SelectionAndCapturesList new_selections;
|
SelectionList new_selections;
|
||||||
for (auto& sel : m_selections)
|
for (auto& sel : m_selections)
|
||||||
{
|
{
|
||||||
SelectionAndCapturesList res = selector(sel.selection);
|
SelectionList res = selector(sel);
|
||||||
for (auto& sel_and_cap : res)
|
for (auto& new_sel : res)
|
||||||
{
|
{
|
||||||
// preserve captures when selectors captures nothing.
|
// preserve captures when selectors captures nothing.
|
||||||
if (sel_and_cap.captures.empty())
|
if (new_sel.captures().empty())
|
||||||
new_selections.emplace_back(sel_and_cap.selection, sel.captures);
|
new_selections.emplace_back(new_sel.first(), new_sel.last(),
|
||||||
|
sel.captures());
|
||||||
else
|
else
|
||||||
new_selections.push_back(std::move(sel_and_cap));
|
new_selections.push_back(std::move(new_sel));
|
||||||
}
|
}
|
||||||
}
|
}
|
||||||
if (new_selections.empty())
|
if (new_selections.empty())
|
||||||
|
@ -403,7 +404,7 @@ IncrementalInserter::IncrementalInserter(Editor& editor, InsertMode mode)
|
||||||
--first;
|
--first;
|
||||||
if (last.underlying_iterator().is_end())
|
if (last.underlying_iterator().is_end())
|
||||||
--last;
|
--last;
|
||||||
sel.selection = Selection(first.underlying_iterator(), last.underlying_iterator());
|
sel = Selection(first.underlying_iterator(), last.underlying_iterator());
|
||||||
}
|
}
|
||||||
if (mode == InsertMode::OpenLineBelow or mode == InsertMode::OpenLineAbove)
|
if (mode == InsertMode::OpenLineBelow or mode == InsertMode::OpenLineAbove)
|
||||||
{
|
{
|
||||||
|
@ -414,7 +415,7 @@ IncrementalInserter::IncrementalInserter(Editor& editor, InsertMode mode)
|
||||||
{
|
{
|
||||||
// special case, the --first line above did nothing, so we need to compensate now
|
// special case, the --first line above did nothing, so we need to compensate now
|
||||||
if (sel.first() == utf8::next(buffer.begin()))
|
if (sel.first() == utf8::next(buffer.begin()))
|
||||||
sel.selection = Selection(buffer.begin(), buffer.begin());
|
sel = Selection(buffer.begin(), buffer.begin());
|
||||||
}
|
}
|
||||||
}
|
}
|
||||||
}
|
}
|
||||||
|
@ -426,7 +427,7 @@ IncrementalInserter::~IncrementalInserter()
|
||||||
{
|
{
|
||||||
if (m_mode == InsertMode::Append)
|
if (m_mode == InsertMode::Append)
|
||||||
sel = Selection(sel.first(), utf8::previous(sel.last()));
|
sel = Selection(sel.first(), utf8::previous(sel.last()));
|
||||||
sel.selection.avoid_eol();
|
sel.avoid_eol();
|
||||||
}
|
}
|
||||||
|
|
||||||
m_editor.on_incremental_insertion_end();
|
m_editor.on_incremental_insertion_end();
|
||||||
|
@ -437,7 +438,7 @@ void IncrementalInserter::insert(String content)
|
||||||
Buffer& buffer = m_editor.buffer();
|
Buffer& buffer = m_editor.buffer();
|
||||||
for (auto& sel : m_editor.m_selections)
|
for (auto& sel : m_editor.m_selections)
|
||||||
{
|
{
|
||||||
m_editor.filters()(buffer, sel.selection, content);
|
m_editor.filters()(buffer, sel, content);
|
||||||
buffer.insert(sel.last(), content);
|
buffer.insert(sel.last(), content);
|
||||||
}
|
}
|
||||||
}
|
}
|
||||||
|
|
|
@ -39,8 +39,8 @@ enum class InsertMode : unsigned
|
||||||
class Editor : public SafeCountable
|
class Editor : public SafeCountable
|
||||||
{
|
{
|
||||||
public:
|
public:
|
||||||
typedef std::function<SelectionAndCaptures (const Selection&)> Selector;
|
typedef std::function<Selection (const Selection&)> Selector;
|
||||||
typedef std::function<SelectionAndCapturesList (const Selection&)> MultiSelector;
|
typedef std::function<SelectionList (const Selection&)> MultiSelector;
|
||||||
|
|
||||||
Editor(Buffer& buffer);
|
Editor(Buffer& buffer);
|
||||||
virtual ~Editor() {}
|
virtual ~Editor() {}
|
||||||
|
@ -65,10 +65,10 @@ public:
|
||||||
void select(const BufferIterator& iterator);
|
void select(const BufferIterator& iterator);
|
||||||
void select(const Selector& selector,
|
void select(const Selector& selector,
|
||||||
SelectMode mode = SelectMode::Replace);
|
SelectMode mode = SelectMode::Replace);
|
||||||
void select(SelectionAndCapturesList selections);
|
void select(SelectionList selections);
|
||||||
void multi_select(const MultiSelector& selector);
|
void multi_select(const MultiSelector& selector);
|
||||||
|
|
||||||
const SelectionAndCapturesList& selections() const { return m_selections; }
|
const SelectionList& selections() const { return m_selections; }
|
||||||
std::vector<String> selections_content() const;
|
std::vector<String> selections_content() const;
|
||||||
|
|
||||||
bool undo();
|
bool undo();
|
||||||
|
@ -95,7 +95,7 @@ private:
|
||||||
virtual void on_incremental_insertion_end() {}
|
virtual void on_incremental_insertion_end() {}
|
||||||
|
|
||||||
safe_ptr<Buffer> m_buffer;
|
safe_ptr<Buffer> m_buffer;
|
||||||
SelectionAndCapturesList m_selections;
|
SelectionList m_selections;
|
||||||
FilterGroup m_filters;
|
FilterGroup m_filters;
|
||||||
};
|
};
|
||||||
|
|
||||||
|
|
|
@ -28,6 +28,7 @@ colalias identifier cyan
|
||||||
colalias string magenta
|
colalias string magenta
|
||||||
colalias error default,red
|
colalias error default,red
|
||||||
colalias keyword blue
|
colalias keyword blue
|
||||||
|
colalias operator yellow
|
||||||
colalias attribute green
|
colalias attribute green
|
||||||
colalias comment cyan
|
colalias comment cyan
|
||||||
colalias macro magenta
|
colalias macro magenta
|
||||||
|
|
12
src/main.cc
12
src/main.cc
|
@ -242,7 +242,7 @@ void do_indent(Context& context)
|
||||||
String indent(' ', width);
|
String indent(' ', width);
|
||||||
|
|
||||||
Editor& editor = context.editor();
|
Editor& editor = context.editor();
|
||||||
SelectionAndCapturesList sels = editor.selections();
|
SelectionList sels = editor.selections();
|
||||||
auto restore_sels = on_scope_end([&]{ editor.select(std::move(sels)); });
|
auto restore_sels = on_scope_end([&]{ editor.select(std::move(sels)); });
|
||||||
editor.select(select_whole_lines);
|
editor.select(select_whole_lines);
|
||||||
editor.multi_select(std::bind(select_all_matches, _1, "^[^\n]"));
|
editor.multi_select(std::bind(select_all_matches, _1, "^[^\n]"));
|
||||||
|
@ -253,7 +253,7 @@ void do_deindent(Context& context)
|
||||||
{
|
{
|
||||||
int width = context.options()["indentwidth"].as_int();
|
int width = context.options()["indentwidth"].as_int();
|
||||||
Editor& editor = context.editor();
|
Editor& editor = context.editor();
|
||||||
SelectionAndCapturesList sels = editor.selections();
|
SelectionList sels = editor.selections();
|
||||||
auto restore_sels = on_scope_end([&]{ editor.select(std::move(sels)); });
|
auto restore_sels = on_scope_end([&]{ editor.select(std::move(sels)); });
|
||||||
editor.select(select_whole_lines);
|
editor.select(select_whole_lines);
|
||||||
editor.multi_select(std::bind(select_all_matches, _1,
|
editor.multi_select(std::bind(select_all_matches, _1,
|
||||||
|
@ -266,7 +266,7 @@ void do_select_object(Context& context)
|
||||||
{
|
{
|
||||||
context.input_handler().on_next_key(
|
context.input_handler().on_next_key(
|
||||||
[](const Key& key, Context& context) {
|
[](const Key& key, Context& context) {
|
||||||
typedef std::function<SelectionAndCaptures (const Selection&)> Selector;
|
typedef std::function<Selection (const Selection&)> Selector;
|
||||||
static const std::unordered_map<Key, Selector> key_to_selector =
|
static const std::unordered_map<Key, Selector> key_to_selector =
|
||||||
{
|
{
|
||||||
{ { Key::Modifiers::None, '(' }, std::bind(select_surrounding, _1, std::pair<char, char>{ '(', ')' }, inner) },
|
{ { Key::Modifiers::None, '(' }, std::bind(select_surrounding, _1, std::pair<char, char>{ '(', ')' }, inner) },
|
||||||
|
@ -376,7 +376,7 @@ void jump(Context& context)
|
||||||
auto& manager = ClientManager::instance();
|
auto& manager = ClientManager::instance();
|
||||||
context.change_editor(manager.get_unused_window_for_buffer(buffer));
|
context.change_editor(manager.get_unused_window_for_buffer(buffer));
|
||||||
}
|
}
|
||||||
context.editor().select(SelectionAndCapturesList{ jump });
|
context.editor().select(SelectionList{ jump });
|
||||||
}
|
}
|
||||||
|
|
||||||
String runtime_directory()
|
String runtime_directory()
|
||||||
|
@ -592,8 +592,8 @@ void register_registers()
|
||||||
register_manager.register_dynamic_register('0'+i,
|
register_manager.register_dynamic_register('0'+i,
|
||||||
[i](const Context& context) {
|
[i](const Context& context) {
|
||||||
std::vector<String> result;
|
std::vector<String> result;
|
||||||
for (auto& sel_and_cap : context.editor().selections())
|
for (auto& sel : context.editor().selections())
|
||||||
result.emplace_back(i < sel_and_cap.captures.size() ? sel_and_cap.captures[i] : "");
|
result.emplace_back(i < sel.captures().size() ? sel.captures()[i] : "");
|
||||||
return result;
|
return result;
|
||||||
});
|
});
|
||||||
}
|
}
|
||||||
|
|
|
@ -5,15 +5,42 @@
|
||||||
namespace Kakoune
|
namespace Kakoune
|
||||||
{
|
{
|
||||||
|
|
||||||
Selection::Selection(const BufferIterator& first, const BufferIterator& last)
|
void Range::merge_with(const Range& range)
|
||||||
: m_first(first), m_last(last)
|
{
|
||||||
|
if (m_first < m_last)
|
||||||
|
m_first = std::min(m_first, range.m_first);
|
||||||
|
if (m_first > m_last)
|
||||||
|
m_first = std::max(m_first, range.m_first);
|
||||||
|
m_last = range.m_last;
|
||||||
|
}
|
||||||
|
|
||||||
|
BufferIterator Range::begin() const
|
||||||
|
{
|
||||||
|
return std::min(m_first, m_last);
|
||||||
|
}
|
||||||
|
|
||||||
|
BufferIterator Range::end() const
|
||||||
|
{
|
||||||
|
return utf8::next(std::max(m_first, m_last));
|
||||||
|
}
|
||||||
|
|
||||||
|
Selection::Selection(const BufferIterator& first, const BufferIterator& last,
|
||||||
|
CaptureList captures)
|
||||||
|
: Range{first, last}, m_captures{std::move(captures)}
|
||||||
{
|
{
|
||||||
check_invariant();
|
check_invariant();
|
||||||
register_with_buffer();
|
register_with_buffer();
|
||||||
}
|
}
|
||||||
|
|
||||||
Selection::Selection(const Selection& other)
|
Selection::Selection(const Selection& other)
|
||||||
: m_first(other.m_first), m_last(other.m_last)
|
: Range(other), m_captures(other.m_captures)
|
||||||
|
{
|
||||||
|
register_with_buffer();
|
||||||
|
}
|
||||||
|
|
||||||
|
Selection::Selection(Selection&& other)
|
||||||
|
: Range{other},
|
||||||
|
m_captures{std::move(other.m_captures)}
|
||||||
{
|
{
|
||||||
register_with_buffer();
|
register_with_buffer();
|
||||||
}
|
}
|
||||||
|
@ -25,12 +52,13 @@ Selection::~Selection()
|
||||||
|
|
||||||
Selection& Selection::operator=(const Selection& other)
|
Selection& Selection::operator=(const Selection& other)
|
||||||
{
|
{
|
||||||
const bool new_buffer = &m_first.buffer() != &other.m_first.buffer();
|
const bool new_buffer = &first().buffer() != &other.first().buffer();
|
||||||
if (new_buffer)
|
if (new_buffer)
|
||||||
unregister_with_buffer();
|
unregister_with_buffer();
|
||||||
|
|
||||||
m_first = other.m_first;
|
first() = other.first();
|
||||||
m_last = other.m_last;
|
last() = other.last();
|
||||||
|
m_captures = other.m_captures;
|
||||||
|
|
||||||
if (new_buffer)
|
if (new_buffer)
|
||||||
register_with_buffer();
|
register_with_buffer();
|
||||||
|
@ -38,23 +66,20 @@ Selection& Selection::operator=(const Selection& other)
|
||||||
return *this;
|
return *this;
|
||||||
}
|
}
|
||||||
|
|
||||||
BufferIterator Selection::begin() const
|
Selection& Selection::operator=(Selection&& other)
|
||||||
{
|
{
|
||||||
return std::min(m_first, m_last);
|
const bool new_buffer = &first().buffer() != &other.first().buffer();
|
||||||
}
|
if (new_buffer)
|
||||||
|
unregister_with_buffer();
|
||||||
|
|
||||||
BufferIterator Selection::end() const
|
first() = other.first();
|
||||||
{
|
last() = other.last();
|
||||||
return utf8::next(std::max(m_first, m_last));
|
m_captures = std::move(other.m_captures);
|
||||||
}
|
|
||||||
|
|
||||||
void Selection::merge_with(const Selection& selection)
|
if (new_buffer)
|
||||||
{
|
register_with_buffer();
|
||||||
if (m_first < m_last)
|
|
||||||
m_first = std::min(m_first, selection.m_first);
|
return *this;
|
||||||
if (m_first > m_last)
|
|
||||||
m_first = std::max(m_first, selection.m_first);
|
|
||||||
m_last = selection.m_last;
|
|
||||||
}
|
}
|
||||||
|
|
||||||
static void avoid_eol(BufferIterator& it)
|
static void avoid_eol(BufferIterator& it)
|
||||||
|
@ -66,38 +91,38 @@ static void avoid_eol(BufferIterator& it)
|
||||||
|
|
||||||
void Selection::avoid_eol()
|
void Selection::avoid_eol()
|
||||||
{
|
{
|
||||||
Kakoune::avoid_eol(m_first);
|
Kakoune::avoid_eol(first());
|
||||||
Kakoune::avoid_eol(m_last);
|
Kakoune::avoid_eol(last());
|
||||||
}
|
}
|
||||||
|
|
||||||
void Selection::on_insert(const BufferIterator& begin, const BufferIterator& end)
|
void Selection::on_insert(const BufferIterator& begin, const BufferIterator& end)
|
||||||
{
|
{
|
||||||
m_first.on_insert(begin.coord(), end.coord());
|
first().on_insert(begin.coord(), end.coord());
|
||||||
m_last.on_insert(begin.coord(), end.coord());
|
last().on_insert(begin.coord(), end.coord());
|
||||||
check_invariant();
|
check_invariant();
|
||||||
}
|
}
|
||||||
|
|
||||||
void Selection::on_erase(const BufferIterator& begin, const BufferIterator& end)
|
void Selection::on_erase(const BufferIterator& begin, const BufferIterator& end)
|
||||||
{
|
{
|
||||||
m_first.on_erase(begin.coord(), end.coord());
|
first().on_erase(begin.coord(), end.coord());
|
||||||
m_last.on_erase(begin.coord(), end.coord());
|
last().on_erase(begin.coord(), end.coord());
|
||||||
check_invariant();
|
check_invariant();
|
||||||
}
|
}
|
||||||
|
|
||||||
void Selection::register_with_buffer()
|
void Selection::register_with_buffer()
|
||||||
{
|
{
|
||||||
m_first.buffer().add_change_listener(*this);
|
first().buffer().add_change_listener(*this);
|
||||||
}
|
}
|
||||||
|
|
||||||
void Selection::unregister_with_buffer()
|
void Selection::unregister_with_buffer()
|
||||||
{
|
{
|
||||||
m_first.buffer().remove_change_listener(*this);
|
first().buffer().remove_change_listener(*this);
|
||||||
}
|
}
|
||||||
|
|
||||||
void Selection::check_invariant() const
|
void Selection::check_invariant() const
|
||||||
{
|
{
|
||||||
assert(utf8::is_character_start(m_first));
|
assert(utf8::is_character_start(first()));
|
||||||
assert(utf8::is_character_start(m_last));
|
assert(utf8::is_character_start(last()));
|
||||||
}
|
}
|
||||||
|
|
||||||
}
|
}
|
||||||
|
|
|
@ -6,34 +6,51 @@
|
||||||
namespace Kakoune
|
namespace Kakoune
|
||||||
{
|
{
|
||||||
|
|
||||||
// A Selection holds a buffer range
|
// An oriented, inclusive buffer range
|
||||||
//
|
struct Range
|
||||||
// The Selection class manage a (first, last) buffer iterators pair.
|
|
||||||
// Selections are oriented, first may be > last, and inclusive.
|
|
||||||
// Selection updates it's iterators according to modifications made
|
|
||||||
// in the buffer.
|
|
||||||
struct Selection : public BufferChangeListener
|
|
||||||
{
|
{
|
||||||
Selection(const BufferIterator& first, const BufferIterator& last);
|
public:
|
||||||
Selection(const Selection& other);
|
Range(const BufferIterator& first, const BufferIterator& last)
|
||||||
~Selection();
|
: m_first{first}, m_last{last} {}
|
||||||
|
|
||||||
Selection& operator=(const Selection& other);
|
void merge_with(const Range& range);
|
||||||
|
|
||||||
|
BufferIterator& first() { return m_first; }
|
||||||
|
BufferIterator& last() { return m_last; }
|
||||||
|
|
||||||
|
const BufferIterator& first() const { return m_first; }
|
||||||
|
const BufferIterator& last() const { return m_last; }
|
||||||
|
|
||||||
// returns min(first, last)
|
// returns min(first, last)
|
||||||
BufferIterator begin() const;
|
BufferIterator begin() const;
|
||||||
// returns max(first, last) + 1
|
// returns max(first, last) + 1
|
||||||
BufferIterator end() const;
|
BufferIterator end() const;
|
||||||
|
|
||||||
const BufferIterator& first() const { return m_first; }
|
private:
|
||||||
const BufferIterator& last() const { return m_last; }
|
BufferIterator m_first;
|
||||||
|
BufferIterator m_last;
|
||||||
|
};
|
||||||
|
|
||||||
BufferIterator& first() { return m_first; }
|
using CaptureList = std::vector<String>;
|
||||||
BufferIterator& last() { return m_last; }
|
|
||||||
|
// A selection is a Range, associated with a CaptureList
|
||||||
|
// that updates itself when the buffer it points to gets modified.
|
||||||
|
struct Selection : public Range, public BufferChangeListener
|
||||||
|
{
|
||||||
|
Selection(const BufferIterator& first, const BufferIterator& last,
|
||||||
|
CaptureList captures = {});
|
||||||
|
Selection(Selection&& other);
|
||||||
|
Selection(const Selection& other);
|
||||||
|
~Selection();
|
||||||
|
|
||||||
|
Selection& operator=(const Selection& other);
|
||||||
|
Selection& operator=(Selection&& other);
|
||||||
|
|
||||||
void merge_with(const Selection& selection);
|
|
||||||
void avoid_eol();
|
void avoid_eol();
|
||||||
|
|
||||||
|
CaptureList& captures() { return m_captures; }
|
||||||
|
const CaptureList& captures() const { return m_captures; }
|
||||||
|
|
||||||
private:
|
private:
|
||||||
void on_insert(const BufferIterator& begin,
|
void on_insert(const BufferIterator& begin,
|
||||||
const BufferIterator& end) override;
|
const BufferIterator& end) override;
|
||||||
|
@ -42,50 +59,19 @@ private:
|
||||||
|
|
||||||
void check_invariant() const;
|
void check_invariant() const;
|
||||||
|
|
||||||
BufferIterator m_first;
|
|
||||||
BufferIterator m_last;
|
|
||||||
|
|
||||||
void register_with_buffer();
|
void register_with_buffer();
|
||||||
void unregister_with_buffer();
|
void unregister_with_buffer();
|
||||||
|
|
||||||
|
CaptureList m_captures;
|
||||||
};
|
};
|
||||||
|
using SelectionList = std::vector<Selection>;
|
||||||
|
|
||||||
typedef std::vector<Selection> SelectionList;
|
inline bool overlaps(const Selection& lhs, const Selection& rhs)
|
||||||
typedef std::vector<String> CaptureList;
|
|
||||||
|
|
||||||
// Selections are often associated with a capture list
|
|
||||||
// like when they are created from a regex match with
|
|
||||||
// capture groups.
|
|
||||||
struct SelectionAndCaptures
|
|
||||||
{
|
|
||||||
Selection selection;
|
|
||||||
CaptureList captures;
|
|
||||||
|
|
||||||
SelectionAndCaptures(const BufferIterator& first,
|
|
||||||
const BufferIterator& last,
|
|
||||||
CaptureList captures_list = {})
|
|
||||||
: selection(first, last), captures(std::move(captures_list)) {}
|
|
||||||
SelectionAndCaptures(const Selection& sel,
|
|
||||||
CaptureList captures_list = {})
|
|
||||||
: selection(sel), captures(std::move(captures_list)) {}
|
|
||||||
|
|
||||||
// helper to access the selection
|
|
||||||
BufferIterator begin() const { return selection.begin(); }
|
|
||||||
BufferIterator end() const { return selection.end(); }
|
|
||||||
|
|
||||||
const BufferIterator& first() const { return selection.first(); }
|
|
||||||
const BufferIterator& last() const { return selection.last(); }
|
|
||||||
};
|
|
||||||
|
|
||||||
inline bool overlaps(const SelectionAndCaptures& lhs,
|
|
||||||
const SelectionAndCaptures& rhs)
|
|
||||||
{
|
{
|
||||||
return (lhs.first() <= rhs.first() and lhs.last() >= rhs.first()) or
|
return (lhs.first() <= rhs.first() and lhs.last() >= rhs.first()) or
|
||||||
(lhs.first() <= rhs.last() and lhs.last() >= rhs.last());
|
(lhs.first() <= rhs.last() and lhs.last() >= rhs.last());
|
||||||
}
|
}
|
||||||
|
|
||||||
|
|
||||||
typedef std::vector<SelectionAndCaptures> SelectionAndCapturesList;
|
|
||||||
|
|
||||||
}
|
}
|
||||||
|
|
||||||
#endif // selection_hh_INCLUDED
|
#endif // selection_hh_INCLUDED
|
||||||
|
|
|
@ -84,7 +84,7 @@ Selection utf8_selection(const Utf8Iterator& first, const Utf8Iterator& last)
|
||||||
typedef boost::regex_iterator<BufferIterator> RegexIterator;
|
typedef boost::regex_iterator<BufferIterator> RegexIterator;
|
||||||
|
|
||||||
template<bool punctuation_is_word>
|
template<bool punctuation_is_word>
|
||||||
SelectionAndCaptures select_to_next_word(const Selection& selection)
|
Selection select_to_next_word(const Selection& selection)
|
||||||
{
|
{
|
||||||
Utf8Iterator begin = selection.last();
|
Utf8Iterator begin = selection.last();
|
||||||
if (categorize<punctuation_is_word>(*begin) !=
|
if (categorize<punctuation_is_word>(*begin) !=
|
||||||
|
@ -103,11 +103,11 @@ SelectionAndCaptures select_to_next_word(const Selection& selection)
|
||||||
|
|
||||||
return utf8_selection(begin, with_end ? end : end-1);
|
return utf8_selection(begin, with_end ? end : end-1);
|
||||||
}
|
}
|
||||||
template SelectionAndCaptures select_to_next_word<false>(const Selection&);
|
template Selection select_to_next_word<false>(const Selection&);
|
||||||
template SelectionAndCaptures select_to_next_word<true>(const Selection&);
|
template Selection select_to_next_word<true>(const Selection&);
|
||||||
|
|
||||||
template<bool punctuation_is_word>
|
template<bool punctuation_is_word>
|
||||||
SelectionAndCaptures select_to_next_word_end(const Selection& selection)
|
Selection select_to_next_word_end(const Selection& selection)
|
||||||
{
|
{
|
||||||
Utf8Iterator begin = selection.last();
|
Utf8Iterator begin = selection.last();
|
||||||
if (categorize<punctuation_is_word>(*begin) !=
|
if (categorize<punctuation_is_word>(*begin) !=
|
||||||
|
@ -126,11 +126,11 @@ SelectionAndCaptures select_to_next_word_end(const Selection& selection)
|
||||||
|
|
||||||
return utf8_selection(begin, with_end ? end : end-1);
|
return utf8_selection(begin, with_end ? end : end-1);
|
||||||
}
|
}
|
||||||
template SelectionAndCaptures select_to_next_word_end<false>(const Selection&);
|
template Selection select_to_next_word_end<false>(const Selection&);
|
||||||
template SelectionAndCaptures select_to_next_word_end<true>(const Selection&);
|
template Selection select_to_next_word_end<true>(const Selection&);
|
||||||
|
|
||||||
template<bool punctuation_is_word>
|
template<bool punctuation_is_word>
|
||||||
SelectionAndCaptures select_to_previous_word(const Selection& selection)
|
Selection select_to_previous_word(const Selection& selection)
|
||||||
{
|
{
|
||||||
Utf8Iterator begin = selection.last();
|
Utf8Iterator begin = selection.last();
|
||||||
|
|
||||||
|
@ -150,10 +150,10 @@ SelectionAndCaptures select_to_previous_word(const Selection& selection)
|
||||||
|
|
||||||
return utf8_selection(begin, with_end ? end : end+1);
|
return utf8_selection(begin, with_end ? end : end+1);
|
||||||
}
|
}
|
||||||
template SelectionAndCaptures select_to_previous_word<false>(const Selection&);
|
template Selection select_to_previous_word<false>(const Selection&);
|
||||||
template SelectionAndCaptures select_to_previous_word<true>(const Selection&);
|
template Selection select_to_previous_word<true>(const Selection&);
|
||||||
|
|
||||||
SelectionAndCaptures select_line(const Selection& selection)
|
Selection select_line(const Selection& selection)
|
||||||
{
|
{
|
||||||
Utf8Iterator first = selection.last();
|
Utf8Iterator first = selection.last();
|
||||||
if (*first == '\n' and not is_end(first + 1))
|
if (*first == '\n' and not is_end(first + 1))
|
||||||
|
@ -168,7 +168,7 @@ SelectionAndCaptures select_line(const Selection& selection)
|
||||||
return utf8_selection(first, last);
|
return utf8_selection(first, last);
|
||||||
}
|
}
|
||||||
|
|
||||||
SelectionAndCaptures select_matching(const Selection& selection)
|
Selection select_matching(const Selection& selection)
|
||||||
{
|
{
|
||||||
std::vector<Codepoint> matching_pairs = { '(', ')', '{', '}', '[', ']', '<', '>' };
|
std::vector<Codepoint> matching_pairs = { '(', ')', '{', '}', '[', ']', '<', '>' };
|
||||||
Utf8Iterator it = selection.last();
|
Utf8Iterator it = selection.last();
|
||||||
|
@ -217,9 +217,9 @@ SelectionAndCaptures select_matching(const Selection& selection)
|
||||||
return selection;
|
return selection;
|
||||||
}
|
}
|
||||||
|
|
||||||
SelectionAndCaptures select_surrounding(const Selection& selection,
|
Selection select_surrounding(const Selection& selection,
|
||||||
const CodepointPair& matching,
|
const CodepointPair& matching,
|
||||||
bool inside)
|
bool inside)
|
||||||
{
|
{
|
||||||
int level = 0;
|
int level = 0;
|
||||||
Utf8Iterator first = selection.last();
|
Utf8Iterator first = selection.last();
|
||||||
|
@ -266,8 +266,8 @@ SelectionAndCaptures select_surrounding(const Selection& selection,
|
||||||
return utf8_selection(first, last);
|
return utf8_selection(first, last);
|
||||||
}
|
}
|
||||||
|
|
||||||
SelectionAndCaptures select_to(const Selection& selection,
|
Selection select_to(const Selection& selection,
|
||||||
Codepoint c, int count, bool inclusive)
|
Codepoint c, int count, bool inclusive)
|
||||||
{
|
{
|
||||||
Utf8Iterator begin = selection.last();
|
Utf8Iterator begin = selection.last();
|
||||||
Utf8Iterator end = begin;
|
Utf8Iterator end = begin;
|
||||||
|
@ -283,8 +283,8 @@ SelectionAndCaptures select_to(const Selection& selection,
|
||||||
return utf8_selection(begin, inclusive ? end : end-1);
|
return utf8_selection(begin, inclusive ? end : end-1);
|
||||||
}
|
}
|
||||||
|
|
||||||
SelectionAndCaptures select_to_reverse(const Selection& selection,
|
Selection select_to_reverse(const Selection& selection,
|
||||||
Codepoint c, int count, bool inclusive)
|
Codepoint c, int count, bool inclusive)
|
||||||
{
|
{
|
||||||
Utf8Iterator begin = selection.last();
|
Utf8Iterator begin = selection.last();
|
||||||
Utf8Iterator end = begin;
|
Utf8Iterator end = begin;
|
||||||
|
@ -300,7 +300,7 @@ SelectionAndCaptures select_to_reverse(const Selection& selection,
|
||||||
return utf8_selection(begin, inclusive ? end : end+1);
|
return utf8_selection(begin, inclusive ? end : end+1);
|
||||||
}
|
}
|
||||||
|
|
||||||
SelectionAndCaptures select_to_eol(const Selection& selection)
|
Selection select_to_eol(const Selection& selection)
|
||||||
{
|
{
|
||||||
Utf8Iterator begin = selection.last();
|
Utf8Iterator begin = selection.last();
|
||||||
Utf8Iterator end = begin + 1;
|
Utf8Iterator end = begin + 1;
|
||||||
|
@ -308,7 +308,7 @@ SelectionAndCaptures select_to_eol(const Selection& selection)
|
||||||
return utf8_selection(begin, end-1);
|
return utf8_selection(begin, end-1);
|
||||||
}
|
}
|
||||||
|
|
||||||
SelectionAndCaptures select_to_eol_reverse(const Selection& selection)
|
Selection select_to_eol_reverse(const Selection& selection)
|
||||||
{
|
{
|
||||||
Utf8Iterator begin = selection.last();
|
Utf8Iterator begin = selection.last();
|
||||||
Utf8Iterator end = begin - 1;
|
Utf8Iterator end = begin - 1;
|
||||||
|
@ -317,7 +317,7 @@ SelectionAndCaptures select_to_eol_reverse(const Selection& selection)
|
||||||
}
|
}
|
||||||
|
|
||||||
template<bool punctuation_is_word>
|
template<bool punctuation_is_word>
|
||||||
SelectionAndCaptures select_whole_word(const Selection& selection, bool inner)
|
Selection select_whole_word(const Selection& selection, bool inner)
|
||||||
{
|
{
|
||||||
Utf8Iterator first = selection.last();
|
Utf8Iterator first = selection.last();
|
||||||
Utf8Iterator last = first;
|
Utf8Iterator last = first;
|
||||||
|
@ -341,10 +341,10 @@ SelectionAndCaptures select_whole_word(const Selection& selection, bool inner)
|
||||||
--last;
|
--last;
|
||||||
return utf8_selection(first, last);
|
return utf8_selection(first, last);
|
||||||
}
|
}
|
||||||
template SelectionAndCaptures select_whole_word<false>(const Selection&, bool);
|
template Selection select_whole_word<false>(const Selection&, bool);
|
||||||
template SelectionAndCaptures select_whole_word<true>(const Selection&, bool);
|
template Selection select_whole_word<true>(const Selection&, bool);
|
||||||
|
|
||||||
SelectionAndCaptures select_whole_lines(const Selection& selection)
|
Selection select_whole_lines(const Selection& selection)
|
||||||
{
|
{
|
||||||
// no need to be utf8 aware for is_eol as we only use \n as line seperator
|
// no need to be utf8 aware for is_eol as we only use \n as line seperator
|
||||||
BufferIterator first = selection.first();
|
BufferIterator first = selection.first();
|
||||||
|
@ -361,14 +361,13 @@ SelectionAndCaptures select_whole_lines(const Selection& selection)
|
||||||
return Selection(first, last);
|
return Selection(first, last);
|
||||||
}
|
}
|
||||||
|
|
||||||
SelectionAndCaptures select_whole_buffer(const Selection& selection)
|
Selection select_whole_buffer(const Selection& selection)
|
||||||
{
|
{
|
||||||
const Buffer& buffer = selection.first().buffer();
|
const Buffer& buffer = selection.first().buffer();
|
||||||
return Selection(buffer.begin(), utf8::previous(buffer.end()));
|
return Selection(buffer.begin(), utf8::previous(buffer.end()));
|
||||||
}
|
}
|
||||||
|
|
||||||
SelectionAndCaptures select_next_match(const Selection& selection,
|
Selection select_next_match(const Selection& selection, const String& regex)
|
||||||
const String& regex)
|
|
||||||
{
|
{
|
||||||
try
|
try
|
||||||
{
|
{
|
||||||
|
@ -403,7 +402,7 @@ SelectionAndCaptures select_next_match(const Selection& selection,
|
||||||
if (begin == end)
|
if (begin == end)
|
||||||
++end;
|
++end;
|
||||||
|
|
||||||
return SelectionAndCaptures(begin, utf8::previous(end), std::move(captures));
|
return Selection(begin, utf8::previous(end), std::move(captures));
|
||||||
}
|
}
|
||||||
catch (boost::regex_error& err)
|
catch (boost::regex_error& err)
|
||||||
{
|
{
|
||||||
|
@ -411,8 +410,7 @@ SelectionAndCaptures select_next_match(const Selection& selection,
|
||||||
}
|
}
|
||||||
}
|
}
|
||||||
|
|
||||||
SelectionAndCapturesList select_all_matches(const Selection& selection,
|
SelectionList select_all_matches(const Selection& selection, const String& regex)
|
||||||
const String& regex)
|
|
||||||
{
|
{
|
||||||
try
|
try
|
||||||
{
|
{
|
||||||
|
@ -420,7 +418,7 @@ SelectionAndCapturesList select_all_matches(const Selection& selection,
|
||||||
RegexIterator re_it(selection.begin(), selection.end(), ex);
|
RegexIterator re_it(selection.begin(), selection.end(), ex);
|
||||||
RegexIterator re_end;
|
RegexIterator re_end;
|
||||||
|
|
||||||
SelectionAndCapturesList result;
|
SelectionList result;
|
||||||
for (; re_it != re_end; ++re_it)
|
for (; re_it != re_end; ++re_it)
|
||||||
{
|
{
|
||||||
BufferIterator begin = (*re_it)[0].first;
|
BufferIterator begin = (*re_it)[0].first;
|
||||||
|
@ -433,9 +431,8 @@ SelectionAndCapturesList select_all_matches(const Selection& selection,
|
||||||
for (auto& match : *re_it)
|
for (auto& match : *re_it)
|
||||||
captures.push_back(String(match.first, match.second));
|
captures.push_back(String(match.first, match.second));
|
||||||
|
|
||||||
result.push_back(SelectionAndCaptures(begin,
|
result.push_back(Selection(begin, begin == end ? end : utf8::previous(end),
|
||||||
begin == end ? end : utf8::previous(end),
|
std::move(captures)));
|
||||||
std::move(captures)));
|
|
||||||
}
|
}
|
||||||
return result;
|
return result;
|
||||||
}
|
}
|
||||||
|
@ -445,8 +442,8 @@ SelectionAndCapturesList select_all_matches(const Selection& selection,
|
||||||
}
|
}
|
||||||
}
|
}
|
||||||
|
|
||||||
SelectionAndCapturesList split_selection(const Selection& selection,
|
SelectionList split_selection(const Selection& selection,
|
||||||
const String& separator_regex)
|
const String& separator_regex)
|
||||||
{
|
{
|
||||||
try
|
try
|
||||||
{
|
{
|
||||||
|
@ -455,7 +452,7 @@ SelectionAndCapturesList split_selection(const Selection& selection,
|
||||||
boost::regex_constants::match_nosubs);
|
boost::regex_constants::match_nosubs);
|
||||||
RegexIterator re_end;
|
RegexIterator re_end;
|
||||||
|
|
||||||
SelectionAndCapturesList result;
|
SelectionList result;
|
||||||
BufferIterator begin = selection.begin();
|
BufferIterator begin = selection.begin();
|
||||||
for (; re_it != re_end; ++re_it)
|
for (; re_it != re_end; ++re_it)
|
||||||
{
|
{
|
||||||
|
|
|
@ -8,44 +8,40 @@ namespace Kakoune
|
||||||
{
|
{
|
||||||
|
|
||||||
template<bool punctuation_is_word>
|
template<bool punctuation_is_word>
|
||||||
SelectionAndCaptures select_to_next_word(const Selection& selection);
|
Selection select_to_next_word(const Selection& selection);
|
||||||
template<bool punctuation_is_word>
|
template<bool punctuation_is_word>
|
||||||
SelectionAndCaptures select_to_next_word_end(const Selection& selection);
|
Selection select_to_next_word_end(const Selection& selection);
|
||||||
template<bool punctuation_is_word>
|
template<bool punctuation_is_word>
|
||||||
SelectionAndCaptures select_to_previous_word(const Selection& selection);
|
Selection select_to_previous_word(const Selection& selection);
|
||||||
|
|
||||||
SelectionAndCaptures select_line(const Selection& selection);
|
|
||||||
SelectionAndCaptures select_matching(const Selection& selection);
|
|
||||||
|
|
||||||
|
Selection select_line(const Selection& selection);
|
||||||
|
Selection select_matching(const Selection& selection);
|
||||||
|
|
||||||
using CodepointPair = std::pair<Codepoint, Codepoint>;
|
using CodepointPair = std::pair<Codepoint, Codepoint>;
|
||||||
SelectionAndCaptures select_surrounding(const Selection& selection,
|
Selection select_surrounding(const Selection& selection,
|
||||||
const CodepointPair& matching,
|
const CodepointPair& matching, bool inside);
|
||||||
bool inside);
|
|
||||||
|
|
||||||
SelectionAndCaptures select_to(const Selection& selection,
|
Selection select_to(const Selection& selection,
|
||||||
Codepoint c,
|
Codepoint c, int count, bool inclusive);
|
||||||
int count, bool inclusive);
|
Selection select_to_reverse(const Selection& selection,
|
||||||
SelectionAndCaptures select_to_reverse(const Selection& selection,
|
Codepoint c, int count, bool inclusive);
|
||||||
Codepoint c,
|
|
||||||
int count, bool inclusive);
|
|
||||||
|
|
||||||
SelectionAndCaptures select_to_eol(const Selection& selection);
|
Selection select_to_eol(const Selection& selection);
|
||||||
SelectionAndCaptures select_to_eol_reverse(const Selection& selection);
|
Selection select_to_eol_reverse(const Selection& selection);
|
||||||
|
|
||||||
template<bool punctuation_is_word>
|
template<bool punctuation_is_word>
|
||||||
SelectionAndCaptures select_whole_word(const Selection& selection, bool inner);
|
Selection select_whole_word(const Selection& selection, bool inner);
|
||||||
SelectionAndCaptures select_whole_lines(const Selection& selection);
|
Selection select_whole_lines(const Selection& selection);
|
||||||
SelectionAndCaptures select_whole_buffer(const Selection& selection);
|
Selection select_whole_buffer(const Selection& selection);
|
||||||
|
|
||||||
SelectionAndCaptures select_next_match(const Selection& selection,
|
Selection select_next_match(const Selection& selection,
|
||||||
const String& regex);
|
const String& regex);
|
||||||
|
|
||||||
SelectionAndCapturesList select_all_matches(const Selection& selection,
|
SelectionList select_all_matches(const Selection& selection,
|
||||||
const String& regex);
|
const String& regex);
|
||||||
|
|
||||||
SelectionAndCapturesList split_selection(const Selection& selection,
|
SelectionList split_selection(const Selection& selection,
|
||||||
const String& separator_regex);
|
const String& separator_regex);
|
||||||
|
|
||||||
}
|
}
|
||||||
|
|
||||||
|
|
|
@ -175,7 +175,7 @@ String Window::status_line() const
|
||||||
|
|
||||||
void Window::on_incremental_insertion_end()
|
void Window::on_incremental_insertion_end()
|
||||||
{
|
{
|
||||||
SelectionAndCapturesList backup(selections());
|
SelectionList backup(selections());
|
||||||
hooks().run_hook("InsertEnd", "", Context(*this));
|
hooks().run_hook("InsertEnd", "", Context(*this));
|
||||||
select(backup);
|
select(backup);
|
||||||
}
|
}
|
||||||
|
|
Loading…
Reference in New Issue
Block a user