Bug 411056 - Elliptical selection tool behaves weird
Summary: Elliptical selection tool behaves weird
Status: RESOLVED FIXED
Alias: None
Product: krita
Classification: Applications
Component: Tools/Selection (show other bugs)
Version: 4.2.5
Platform: Microsoft Windows Microsoft Windows
: NOR normal
Target Milestone: ---
Assignee: Dmitry Kazakov
URL:
Keywords:
Depends on:
Blocks:
 
Reported: 2019-08-19 11:14 UTC by Andreas
Modified: 2020-06-02 12:02 UTC (History)
3 users (show)

See Also:
Latest Commit:
Version Fixed In:


Attachments
File with odd selections. (1.58 MB, application/x-krita)
2019-08-19 11:19 UTC, wolthera
Details
Bug reproduced with normal shapes (41.06 KB, image/png)
2020-05-12 12:45 UTC, Dmitry Kazakov
Details

Note You need to log in before you can comment on or make changes to this bug.
Description Andreas 2019-08-19 11:14:53 UTC
SUMMARY
Elliptical selection tool behaves weird

STEPS TO REPRODUCE
1. Create 1900x1080 image, resolution 1000ppi, 32-bit float/channel - Profile sRGB-elle-V2-g10.icc
2. Make sure tool options are set to: Vector selection
3. Zoom to 400%
4. Start to draw a couple of ellipses

OBSERVED RESULT
https://www.youtube.com/watch?v=HfW5UXnXU90&feature=youtu.be

It seems to be related to the size of the ellipses. When I draw big ones, I need only around 5 for the effect to appear. When I draw smaller ones it takes around  7-8. Also works with 3 bigger ellipses on a 400% zoom. Sometimes one needs to zoom closer AFTER drawing to see the effect

EXPECTED RESULT
Ellipses don't turn into polygons

SOFTWARE/OS VERSIONS
Windows 10 Pro 64bit

KRITA VERSION
4.2.5 64bit

ADDITIONAL INFORMATION
none
Comment 1 wolthera 2019-08-19 11:19:02 UTC
Created attachment 122241 [details]
File with odd selections.

Yeah, I can reproduce this.

mode: vector
action: replace

I think it might actually be the union boolean operator freaking out? This only really happens when using shift+draw.

Last time I got this, the selection width and height of the last drawn ellipse were 21 high and 24 wide.
Comment 2 Halla Rempt 2019-08-27 12:18:44 UTC
We're not sure we can actually fix this, since it's part of the way QPainterPath works. Almost a duplicate of 381925?
Comment 3 Dmitry Kazakov 2020-05-12 11:44:10 UTC
The main problem happens in QPathClipper::clip(). If the newly added ellipse does *not* intersect with the bounding rect of the original selection, then it is just added to the original path with full quality without any clipping. Although if the original bounding rect intersects the new ellipse, then clipping algorithm starts and breaks the curves into segments.
Comment 4 Dmitry Kazakov 2020-05-12 12:45:02 UTC
Okay, the bug is related to bug 381925, but it is different and may be fixed without rewriting Qt's paths code.

The problem is that we measure all our shapes (and vector selections) in 'pt' units. And Qt has heuristic algorithm for linearization of the curves when clipping, and this algorithm uses absolute measurements of the path to split it.

The fix for the bug should include:

1) Make KisShapeSelection use image pixels instead of points
2) Make KisShapeLayer use image pixels as a base coordinate system instead of points as well (the bug is reproducible with normal shapes as well)
3) Make KisShapeLayer::transform() actually transform shapes instead of applying a higher-level matrix on the top of them.

As an alternative, we could just make a simple function for boolean transformation of QPainterPath in the shapes, which would upscale them into a proper scale. The only drawback is that we should locate all the places where we use path-boolean-operations for that.
Comment 5 Dmitry Kazakov 2020-05-12 12:45:32 UTC
Created attachment 128387 [details]
Bug reproduced with normal shapes
Comment 6 Dmitry Kazakov 2020-05-12 18:49:00 UTC
Git commit 64e4de6c6c80686281cdb74a53eaf88ddafd6b5a by Dmitry Kazakov.
Committed on 12/05/2020 at 18:48.
Pushed by dkazakov into branch 'master'.

Add a workaround for boolean operations on shapes

The problem is that Qt's path boolean operation do not support curves,
therefore all the curves are converted into lines
(see QPathSegments::addPath()). The curves are split into lines using
absolute size of the curve for the threshold. Therefore, when applying
boolean operations we should convert them into 'image pixel' coordinate
space first.

M  +7    -0    libs/image/krita_utils.cpp
M  +17   -0    libs/image/krita_utils.h
M  +13   -5    libs/ui/flake/kis_shape_selection.cpp
M  +9    -1    libs/ui/tool/kis_selection_tool_helper.cpp
M  +12   -1    plugins/tools/defaulttool/defaulttool/DefaultTool.cpp

https://invent.kde.org/kde/krita/commit/64e4de6c6c80686281cdb74a53eaf88ddafd6b5a
Comment 7 Dmitry Kazakov 2020-06-02 12:02:00 UTC
Git commit 8a5135870197c5d93f9aac7f8cb67d9389a7503a by Dmitry Kazakov.
Committed on 02/06/2020 at 10:06.
Pushed by dkazakov into branch 'krita/4.3'.

Add a workaround for boolean operations on shapes

The problem is that Qt's path boolean operation do not support curves,
therefore all the curves are converted into lines
(see QPathSegments::addPath()). The curves are split into lines using
absolute size of the curve for the threshold. Therefore, when applying
boolean operations we should convert them into 'image pixel' coordinate
space first.

M  +7    -0    libs/image/krita_utils.cpp
M  +17   -0    libs/image/krita_utils.h
M  +13   -5    libs/ui/flake/kis_shape_selection.cpp
M  +9    -1    libs/ui/tool/kis_selection_tool_helper.cpp
M  +12   -1    plugins/tools/defaulttool/defaulttool/DefaultTool.cpp

https://invent.kde.org/graphics/krita/commit/8a5135870197c5d93f9aac7f8cb67d9389a7503a