The knife tool can now make cuts in multi-object edit mode which cross over multiple objects and go from the geometry of one object to multiple others.
Previously, object switching functionality was implemented but this proved insufficient to achieve the functionality contained within this patch. Instead, the dependence on a singular Object and BMEditMesh stored in the KnifeTool_OpData struct needed to be entirely removed.
This has resulted in a lot of passing around of Object pointers which could potentially be simplified using a map of some kind in the future. For now it works well.
This patch migrates the knife tool code to use world space coordinates instead of object space.
This is required to implement the ability to cut across multiple objects at once and the ability to use the geometry of other objects as a cutting reference.
This introduces precision errors for objects with very large scale or location, however it may be possible to add a switch between world space and object space coordinates depending on whether the user is in multi-object edit mode or not.
After receiving feedback on devtalk, users expressed they wished to be able to cut along an edge so they could make further cuts from a new position along the edge.
This also adds the potential to implement snapping to a given distance along an edge.
When using relative constrained angle mode along an edge which has a face hidden from view, if a cut is added it can sometimes place the previous cut vertex in space, away from the edge.
This was caused by knife_snap_edge_constrained not working correctly when a cut is constrained along the edge it was started from.
Fixed by adding a quick check.
The parameters to ED_transform_calc_orientation_from_type_ex needed to be changed after a merge from master.
This fixed axis constraint for the knife tool.
Knife tool xray (depth testing) was previously only toggle-able by the 'V' modal key.
This patch exposes an RNA boolean in the knife tool settings for toggling xray.
Entering a value for angle snapping increment using the numpad was only allowed once.
To re-enter a value angle snapping had to be toggled off and back on.
Now you can repeatedly re-enter values, except values cannot have decimal points.
If a more precise angle is required, the knife tool settings exposes the angle snapping increment.
This patch adds the ability to press 'R' to cycle through edges to snap relative to when in local angle snapping mode.
The current edge is highlighted yellow and visible angle measurements are always drawn to that edge if enabled.
Adds two new enums to the knife tool settings to select between angle snapping modes and measurement modes.
In the top bar these are displayed inside the popover.
Adds a custom Knife BVH which works with multiple BMesh's to replace the old BMBVH.
Currently, the new BVH is used in a functionally equivalent way to the old BMBVH but avoids re-allocating BVH's in multi-object edit mode.
This makes the current code slightly more complex, but will be incredibly useful when converting the knife tool code from object to world space, something that will need to be done to implement a better multi-object edit mode and further improvements to the tool.
Currently D is used for visual distance and angle measurements but this may be more suited to distance snapping in the future.
Thefore, I am moving it to 'S' and freeing up 'D'.
Now you can create cuts on all objects in multi object edit mode.
- If a cut is started on a given object it can interact with that same object.
- The current object to be cut is switched based on the nearest edge to the mouse cursor, only when the tool mode is idle.
- When a cut is started in empty space it will interact with the last object the mouse was nearest before the cut was started.
Further improvements could include starting a cut in empty space interacting with the current object the mouse is nearest and allocating BMBVH's for each object on tool init instead of every time an object switch occurs.
Visual angle measurements for the knife tool did not work well with vertices.
There were lots of buggy cases which this patch solves.
It also cleans up some of the old visual distance and angle measurements code.
Fixed undo with cut segments along mesh edges and cut segments not over a mesh.
Cut segments along a mesh edge also no longer show as they are redundant.
Midpoint snapping was originally CTRL but when undo was added as CTRL-Z this caused some strange behaviour.
Therefore midpoint snapping was moved to ALT but this broke when alt-tabbing.
By moving midpoint snapping to SHIFT and ignore snapping to CTRL there are no more problems.
Pressing 'V' will toggle depth testing on and off for the knife tool cut lines.
When a cut involves a lot of cut segments on an object it can be very helpful to hide cut segments which should be blocked from view by the object that is being cut.
Previously when a knife cut was created by holding left click and dragging, undo would only undo each segment of the dragged cut individually.
This change makes it so the entire dragged cut is removed when undone.
Some refactors to the undo code were required to implement this.
Moved data required for distance and angle measurements into new struct KnifeMeasureData.
Now this struct is saved on the undo stack which fixes distance and angle measurements when undo is used.
The number of new cuts recorded each undo frame was set based on linehits.
This broke when cut through was enabled.
Solution was to increment the new cuts count every time #knife_add_single_cut is ran.
Pressing ctrl-z will now undo the most recent cut segment made.
When drag cutting undo reverts each segment of the cut individually.
Currently this breaks visible distance and angle measurements after using undo but a fix will be committed soon.
It is dangerous to have 'E' be able to cancel a user's entire cut as it is a key many could accidentally hit and there is no way to retrieve a lost cut. Removing it leaves 'Esc' as the key for cancelling a cut.
On many keyboards 'M' is far away from the other modal keys for the knife tool. 'D' allows for a better workflow by being closer.
When using constrained angle mode, pressing C once will bring you to the current screen-space mode and pressing it again will now enter a new "local" mode.
This mode will snap along the plane of the current cut segment's face.
In the case where the cut was started on a edge or vertex it will snap along the plane of the current face the mouse is over, if this face is adjacent to that edge or vertex.
It made sense to implement a mode that works in this way after adding visible distance and angle measurements as now a user can snap the visible angle for the current cut.
This patch displays the current angle, relative to the positive X axis, in the header/footer when the knife tool is in constrained angle mode.
It also updates constrained angle mode to snap relative to the positive X axis in screen space (previously positive Y).
Pressing M while using the knife tool will now cycle through showing various measurements related to the current cut.
The different modes are:
Just Distance - Shows the length of the current cut segment
Just Angles - If the cut segment is touching any edges the corresponding angle is displayed
Both - Shows both distance and angles
Currently, when a user uses the number keys to input a new snapping angle increment in constrained angle mode it does not visually update until the mouse is jiggled.
This patch solves this problem so it now updates as each number is typed.
- Pressing X, Y or Z will lock current cut to corresponding axis.
- Pressing the same key twice will lock to local object axis.
- Scene orientation setting takes priority over this when set to anything other than global. This provides support for custom orientations.
This is the first commit for the GSOC 2021 Knife Tool Improvements project. It implements D10853 which adds more control over constrained angle mode through new UI elements and number key input.
2021-06-05 14:21:01 +01:00
7 changed files with 2291 additions and 564 deletions
Blocking a user prevents them from interacting with repositories, such as opening or commenting on pull requests or issues. Learn more about blocking a user.