cutBetweenPoints() Knife tool quirk

Posting this in case anyone else runs into a similar situation when using layer.cutBetweenPoints()—the Python API version of the Knife tool. Very important workaround to know about.

The Issue:

When the “cut line” intersects points, the results can be strange and unexpected. It might add new points, floating and separate from the paths, near the intersecting point you tried to cut through. Or, it might connect two separate paths, as shown here…

▲ Expected result

▲ Actual result

▲ Actual result (paths pulled apart to see what’s going on)

At first I thought the solution might be to perform a series of cuts, rather than a single cut through all paths. I spent a whole day writing a script to determine which parts of the cut line went through positive “black” space and which through negative “white” space, then perform cuts through the positive space. This solved the above example of accidentally connected paths, but it still had issues when cutting through points. For example, when cutting through the O glyph’s two circular paths, if one of the on-curve points had a Y position of 300, and I cut horizontally across all paths at 300, that part of the O would not cut in half. Instead, some extra points would be created that float nearby the point I tried to cut through.

The Solution:

Instead of cutting along a grid line (for example, horizontally at a Y position of 300), cut nearby that point—like at 300.1 . Points snap to the grid, and so will the results of the Knife / cutBetweenPoints() operation; but the cut line itself can be anywhere in between grid lines.

Painfully simple. I threw away the day’s worth of code I’d written, and adopted this solution. It works reliably. I also assume this is why the issue is so rare when using the Knife tool—when we click with a pointer, the computer registers our click position with super high precision (ex: coordinates might be 4.0001, 300.019999 instead of 4, 300), so it’s super unlikely that we’ll cut directly through a point.

@GeorgSeifert, if this behavior and workaround is avoidable, it would be a great improvement.

I think I fixed this. Lets see what other edge cases will pop up.

1 Like