Skip to content

Conversation

@zeux
Copy link
Owner

@zeux zeux commented Nov 29, 2025

Collapsing all wedges into a single wedge for complex-complex collapses
is simple but results in high-error collapses alongside attribute
discontinuities. This is a problem because it either results in poor
attribute quality, or in poor geometric quality elsewhere as the
simplifier is forced to look for lower error collapses.

This change instead adjusts complex collapses to use parallel collapses
if possible: wedges are collapsed individually towards different wedges
along the original edges. This makes complex collapses work similarly to
seam collapses if possible.

To implement this without extra performance issues, we use loop
metadata. Because loops are really tracking a single incoming/outgoing
half-edge in the original (unwelded) topology, a typical attribute
discontinuity will have X wedges (seams only have 2), and each of the
wedges will have their own loop/loopback that correctly trace the
adjoining triangle boundary. Thus we can use these to guide the
collapses.

In some complex topological situations this may not always find the
correct wedge target, but fundamentally complex-complex collapses may
not have a correct wedge target in all cases (if a discontinuity has 3
wedges then any collapse will have to collapse one of them onto a wedge
that was not connected to the original). In the future we could use
error or position patching to resolve these cases but that requires
invasive changes with potentially problematic consequences, whereas
using loop metadata should be cheap and safe.

This has no effect on performance on most meshes (and is only applied
for permissive mode); on meshes where almost every vertex is
complex, this costs under 10% performance but results in much better
quality. In general, after this "soft" protection like normal creases is
mostly unnecessary because the simplifier will do the right thing while
it's possible. Protecting UV edges may still be important to avoid UV
distortion, although even without UV protection the quality can remain
quite high if the UVs are weighted properly.

This contribution is sponsored by Valve.

zeux added 4 commits November 29, 2025 08:39
We switch the current (cyan) color to only show complex edges with loop
metadata, similarly to other collapse kinds. For complex-complex edges
that aren't tagged as loops, we instead use a darker magenta.

Both can be collapsed but the non-loop edges usually have a higher error
and will use a slightly different logic in the next commit.
Collapsing all wedges into a single wedge for complex-complex collapses
is simple but results in high-error collapses alongside attribute
discontinuities. This is a problem because it either results in poor
attribute quality, or in poor geometric quality elsewhere as the
simplifier is forced to look for lower error collapses.

This change instead adjusts complex collapses to use parallel collapses
if possible: wedges are collapsed individually towards different wedges
along the original edges. This makes complex collapses work similarly to
seam collapses if possible.

To implement this without extra performance issues, we use loop
metadata. Because loops are really tracking a single incoming/outgoing
half-edge in the original (unwelded) topology, a typical attribute
discontinuity will have X wedges (seams only have 2), and each of the
wedges will have their own loop/loopback that correctly trace the
adjoining triangle boundary. Thus we can use these to guide the
collapses.

In some complex topological situations this may not always find the
correct wedge target, but fundamentally complex-complex collapses may
*not* have a correct wedge target in all cases (if a discontinuity has 3
wedges then any collapse will have to collapse one of them onto a wedge
that was not connected to the original). In the future we could use
error or position patching to resolve these cases but that requires
invasive changes with potentially problematic consequences, whereas
using loop metadata should be cheap and safe.

This has no effect on performance on most meshes (and no effect unless
permissive mode is used); on meshes where almost every vertex is
complex, this costs under 10% performance but results in much better
quality. In general, after this "soft" protection like normal creases is
mostly unnecessary because the simplifier will do the right thing while
it's possible. Protecting UV edges may still be important to avoid UV
distortion, although even without UV protection the quality can remain
quite high if the UVs are weighted properly.
In permissive mode we no longer need this as the simplifier will
correctly trace the hard edges by itself. We still keep the option for
testing just in case, but it's no longer preferred and isn't the
default.
Remove normal crease protection from permissive mode example. With
parallel collapses, this should be mostly unnecessary so we should no
longer recommend it in the documentation.
@zeux
Copy link
Owner Author

zeux commented Nov 29, 2025

Example of how this helps on a completely faceted mesh (smaller error & better shading):

before after
image image

Example of how this helps alongside UV seams with high texture weight (high error collapses weren't taken before):

before after
Pasted image 20251128131331 Pasted image 20251128131440

Example of how this helps alongside UV seams with zero texture weight:

before after
image image

With this, permissive mode with enabled protection on UV seams should generally not be worse wrt quality or appearance than not using it, and in some cases it may even be practical to disable UV seam protection, as long as simplifier does have access to UV data with carefully setup weight - the good results in the last comparison are not guaranteed otherwise :) Accordingly it should be unnecessary to protect normal creases so the documentation was updated accordingly.

Permissive mode will remain experimental because there's still cases where behavior is not ideal and there's a few different ways to improve this that may be risky.

@zeux zeux merged commit eb0b0cd into master Nov 30, 2025
13 checks passed
@zeux zeux deleted the simp-permloop branch November 30, 2025 16:59
Sign up for free to join this conversation on GitHub. Already have an account? Sign in to comment

Labels

None yet

Projects

None yet

Development

Successfully merging this pull request may close these issues.

1 participant