summaryrefslogtreecommitdiff
path: root/Userland/Libraries/LibGUI
diff options
context:
space:
mode:
authoriCristalrope <icristalrope@gmail.com>2021-04-21 17:09:04 +0200
committerGitHub <noreply@github.com>2021-04-21 17:09:04 +0200
commit8bb4409a5df3964e9c8fc058a1adc426d29d152e (patch)
treee587be443853143e6e17958d98c86b31c6f95c60 /Userland/Libraries/LibGUI
parentfd43ee09e189a0eaa8acb7af32a1b4d3fd54ca1c (diff)
downloadserenity-8bb4409a5df3964e9c8fc058a1adc426d29d152e.zip
LibGUI: Track selection starting index in AbstractView (#6515)
Modifying the selection while holding the shift button and selecting with the mouse or the arrow keys no longer results in broken selections. Fixes #6279.
Diffstat (limited to 'Userland/Libraries/LibGUI')
-rw-r--r--Userland/Libraries/LibGUI/AbstractView.cpp31
-rw-r--r--Userland/Libraries/LibGUI/AbstractView.h3
2 files changed, 21 insertions, 13 deletions
diff --git a/Userland/Libraries/LibGUI/AbstractView.cpp b/Userland/Libraries/LibGUI/AbstractView.cpp
index 48a4c480bf..9dbda5c75a 100644
--- a/Userland/Libraries/LibGUI/AbstractView.cpp
+++ b/Userland/Libraries/LibGUI/AbstractView.cpp
@@ -91,6 +91,7 @@ void AbstractView::model_did_update(unsigned int flags)
m_drop_candidate_index = {};
selection().remove_matching([this](auto& index) { return !model()->is_valid(index); });
}
+ m_selection_start_index = {};
}
void AbstractView::clear_selection()
@@ -103,6 +104,11 @@ void AbstractView::set_selection(const ModelIndex& new_index)
m_selection.set(new_index);
}
+void AbstractView::set_selection_start_index(const ModelIndex& new_index)
+{
+ m_selection_start_index = new_index;
+}
+
void AbstractView::add_selection(const ModelIndex& new_index)
{
m_selection.add(new_index);
@@ -341,9 +347,10 @@ void AbstractView::mouseup_event(MouseEvent& event)
// in mousedown_event(), because we could be seeing a start of a drag.
// Since we're here, it was not that; so fix up the selection now.
auto index = index_at_event_position(event.position());
- if (index.is_valid())
+ if (index.is_valid()) {
set_selection(index);
- else
+ set_selection_start_index(index);
+ } else
clear_selection();
m_might_drag = false;
update();
@@ -450,20 +457,21 @@ void AbstractView::set_cursor(ModelIndex index, SelectionUpdate selection_update
selection_update = SelectionUpdate::Set;
if (model()->is_valid(index)) {
- if (selection_update == SelectionUpdate::Set)
+ if (selection_update == SelectionUpdate::Set) {
set_selection(index);
- else if (selection_update == SelectionUpdate::Ctrl)
+ set_selection_start_index(index);
+ } else if (selection_update == SelectionUpdate::Ctrl) {
toggle_selection(index);
- else if (selection_update == SelectionUpdate::ClearIfNotSelected) {
+ } else if (selection_update == SelectionUpdate::ClearIfNotSelected) {
if (!m_selection.contains(index))
clear_selection();
} else if (selection_update == SelectionUpdate::Shift) {
- // Toggle all from cursor to new index.
- auto min_row = min(cursor_index().row(), index.row());
- auto max_row = max(cursor_index().row(), index.row());
- auto min_column = min(cursor_index().column(), index.column());
- auto max_column = max(cursor_index().column(), index.column());
+ auto min_row = min(selection_start_index().row(), index.row());
+ auto max_row = max(selection_start_index().row(), index.row());
+ auto min_column = min(selection_start_index().column(), index.column());
+ auto max_column = max(selection_start_index().column(), index.column());
+ clear_selection();
for (auto row = min_row; row <= max_row; ++row) {
for (auto column = min_column; column <= max_column; ++column) {
auto new_index = model()->index(row, column);
@@ -471,9 +479,6 @@ void AbstractView::set_cursor(ModelIndex index, SelectionUpdate selection_update
toggle_selection(new_index);
}
}
-
- // Finally toggle the cursor index again to make it go back to its current state.
- toggle_selection(cursor_index());
}
// FIXME: Support the other SelectionUpdate types
diff --git a/Userland/Libraries/LibGUI/AbstractView.h b/Userland/Libraries/LibGUI/AbstractView.h
index 15018ab301..10cf80d086 100644
--- a/Userland/Libraries/LibGUI/AbstractView.h
+++ b/Userland/Libraries/LibGUI/AbstractView.h
@@ -136,6 +136,7 @@ public:
virtual void scroll_into_view(const ModelIndex&, [[maybe_unused]] bool scroll_horizontally = true, [[maybe_unused]] bool scroll_vertically = true) { }
const ModelIndex& cursor_index() const { return m_cursor_index; }
+ const ModelIndex& selection_start_index() const { return m_selection_start_index; }
void set_cursor(ModelIndex, SelectionUpdate, bool scroll_cursor_into_view = true);
bool is_tab_key_navigation_enabled() const { return m_tab_key_navigation_enabled; }
@@ -163,6 +164,7 @@ protected:
virtual void clear_selection();
virtual void set_selection(const ModelIndex&);
+ virtual void set_selection_start_index(const ModelIndex&);
virtual void add_selection(const ModelIndex&);
virtual void remove_selection(const ModelIndex&);
virtual void toggle_selection(const ModelIndex&);
@@ -206,6 +208,7 @@ protected:
private:
RefPtr<Model> m_model;
ModelSelection m_selection;
+ ModelIndex m_selection_start_index;
String m_searching;
RefPtr<Core::Timer> m_searching_timer;
ModelIndex m_cursor_index;