diff options
author | 2021-01-31 21:30:51 +0100 | |
---|---|---|
committer | 2021-02-13 13:02:54 -0800 | |
commit | e38b78b2aa787e3d1de97fb737601dc30a7fad6b (patch) | |
tree | edac9dafd1bdb94acc184ae767ec9afb80cd808e /stats/scatterseries.cpp | |
parent | d85b3217840656bf371cd64264ee472a68c3141a (diff) | |
download | subsurface-e38b78b2aa787e3d1de97fb737601dc30a7fad6b.tar.gz |
statistics: select multiple dives in scatter-plot by shift-clicking
Somewhat improve selection mechanics in the scatter-plot by
allowing additional selections with shift-clicking. When the
dives under the mouse are already selected, then deselect them.
This appears to be a rather common UI idiom in desktop
applications.
Signed-off-by: Berthold Stoeger <bstoeger@mail.tuwien.ac.at>
Diffstat (limited to 'stats/scatterseries.cpp')
-rw-r--r-- | stats/scatterseries.cpp | 35 |
1 files changed, 31 insertions, 4 deletions
diff --git a/stats/scatterseries.cpp b/stats/scatterseries.cpp index f88837288..fe9889d33 100644 --- a/stats/scatterseries.cpp +++ b/stats/scatterseries.cpp @@ -78,12 +78,39 @@ std::vector<int> ScatterSeries::getItemsUnderMouse(const QPointF &point) const return res; } -void ScatterSeries::selectItemsUnderMouse(const QPointF &point) +void ScatterSeries::selectItemsUnderMouse(const QPointF &point, bool shiftPressed) { std::vector<struct dive *> selected; - - for(int idx: getItemsUnderMouse(point)) - selected.push_back(items[idx].d); + std::vector<int> indices = getItemsUnderMouse(point); + + if (shiftPressed) { + // When shift is pressed, add the items under the mouse to the selection + // or, if all items under the mouse are selected, remove them. + selected = getDiveSelection(); + bool allSelected = std::all_of(indices.begin(), indices.end(), + [this] (int idx) { return items[idx].d->selected; }); + if (allSelected) { + // Remove items under cursor from selection. This could be made more efficient. + for (int idx: indices) { + auto it = std::find(selected.begin(), selected.end(), items[idx].d); + if (it != selected.end()) { + // Move last element to deselected element. If this already was + // the last element, this is a no-op. Then, chop off last element. + *it = selected.back(); + selected.pop_back(); + } + } + } else { + // Add items under cursor to selection + for (int idx: indices) { + if (std::find(selected.begin(), selected.end(), items[idx].d) == selected.end()) + selected.push_back(items[idx].d); + } + } + } else { + for(int idx: indices) + selected.push_back(items[idx].d); + } setSelection(selected, selected.empty() ? nullptr : selected.front()); } |