A way to create drag rects from selection (other than SelectCancel click)
- Dominant language
- C++
- Stars
- 6.2k
- Forks
- 693
- PR merge metrics
- No merged PRs in 30d
Description
Before the query feature got replaced with DragRect, ImPlot had seemed to allow the user to draw the query rect - either with `QueryButton`, or by using box-select with `QueryToggleMod`. With DragRect, it's not clear how to let the user draw the query area.
I don't really like the solution used in the ImPlot demo, where the user needs to click SelectCancel during selection in order to create a DragRect. This gesture is not very intuitive, and might even be difficult for some users. Holding a modifier key during a regular selection would be much easier IMHO.
I'm trying to mimick `QueryToggleMod` on the latest version of ImPlot and I can't figure out a good way to make it work. The main problem is that I cannot handle the mouse-up event _before_ ImPlot does the same, and cancel the selection before ImPlot zooms in.
- I tried to check `ImGui::IsMouseReleased()` on the box-selection button (at the same time checking for the modifier key). If the mouse gets released in the current frame, I save the current selection to a DragRect and call `ImPlot::CancelPlotSelection()` to prevent ImPlot from zooming in.
- If I call `ImPlot::GetPlotSelection()` to retrieve the selection rect, it locks the plot setup. This in turn calls `SetupFinish()`, and finally goes to `UpdateInput()`. The latter sees that the mouse has been released, and zooms in and sets `plot.Selected = false`. As a result, `GetPlotSelection()` _returns an empty rect_.
- As a workaround, I can use a cached selection rect saved on the previous frame - it's not perfect (because the mouse might have moved), but better than nothing. But yeah, it's only a clumsy workaround.
- When I try to cancel the selection on `IsMouseReleased()`, `ImPlot::CancelPlotSelection()` follows the same pattern as `ImPlot::GetPlotSelection()`: it goes to `UpdateInput()` which handles mouse-up on its own, and _commits the selection_ before `CancelPlotSelection()` gets a chance to cancel it. Basically `CancelPlotSelection()` doesn't work in the mouse-up frame, and there's no good solution for that.
- I tried to block `UpdateInput()` by temporarily setting `OverrideMod` to my `QueryToggleMod` so that on the mouse-up frame, ImPlot ignores all user input. This way `CancelPlotSelection()` works if there's a selection rect.
- This is a dirty hack rather than a workaround, and I'd prefer to avoid it.
- In case of `plot.Selecting == true` and `plot.Selected == false` (which occurs when the user hasn't dragged the mouse farther than the threshold), `CancelPlotSelection()` thinks there's no selection and nothing to cancel. As a result, the mouse-up event is totally missed by ImPlot, and it remains in the selection mode even though the mouse button is up. More hacks could probably fix this too, but I decided to draw a line here.
- IMHO, inability of `CancelPlotSelection()` is either a bug that needs to be fixed or, if it's the intended behavior, it should be documented in implot.h.
So what would be the recommended way to create DragRects from user input? If clicking SelectCancel is the only way, can we modify ImPlot to provide some other ways (like `QueryToggleMod`), or to provide some means to implement other ways on the application side?
Contributor guide
No contributing guide indexed for this repository
Assessment
This issue has not been assessed yet.