Commit Graph

52 Commits

Author SHA1 Message Date
d43b5791e0 BLI: Refactor vector types & functions to use templates
This patch implements the vector types (i.e:`float2`) by making heavy
usage of templating. All vector functions are now outside of the vector
classes (inside the `blender::math` namespace) and are not vector size
dependent for the most part.

In the ongoing effort to make shaders less GL centric, we are aiming
to share more code between GLSL and C++ to avoid code duplication.

####Motivations:
- We are aiming to share UBO and SSBO structures between GLSL and C++.
This means we will use many of the existing vector types and others
we currently don't have (uintX, intX). All these variations were
asking for many more code duplication.
- Deduplicate existing code which is duplicated for each vector size.
- We also want to share small functions. Which means that vector
functions should be static and not in the class namespace.
- Reduce friction to use these types in new projects due to their
incompleteness.
- The current state of the `BLI_(float|double|mpq)(2|3|4).hh` is a
bit of a let down. Most clases are incomplete, out of sync with each
others with different codestyles, and some functions that should be
static are not (i.e: `float3::reflect()`).

####Upsides:
- Still support `.x, .y, .z, .w` for readability.
- Compact, readable and easilly extendable.
- All of the vector functions are available for all the vectors types
and can be restricted to certain types. Also template specialization
let us define exception for special class (like mpq).
- With optimization ON, the compiler unroll the loops and performance
is the same.

####Downsides:
- Might impact debugability. Though I would arge that the bugs are
rarelly caused by the vector class itself (since the operations are
quite trivial) but by the type conversions.
- Might impact compile time. I did not saw a significant impact since
the usage is not really widespread.
- Functions needs to be rewritten to support arbitrary vector length.
For instance, one can't call `len_squared_v3v3` in
`math::length_squared()` and call it a day.
- Type cast does not work with the template version of the `math::`
vector functions. Meaning you need to manually cast `float *` and
`(float *)[3]` to `float3` for the function calls.
i.e: `math::distance_squared(float3(nearest.co), positions[i]);`
- Some parts might loose in readability:
`float3::dot(v1.normalized(), v2.normalized())`
becoming
`math::dot(math::normalize(v1), math::normalize(v2))`
But I propose, when appropriate, to use
`using namespace blender::math;` on function local or file scope to
increase readability.
`dot(normalize(v1), normalize(v2))`

####Consideration:
- Include back `.length()` method. It is quite handy and is more C++
oriented.
- I considered the GLM library as a candidate for replacement. It felt
like too much for what we need and would be difficult to extend / modify
to our needs.
- I used Macros to reduce code in operators declaration and potential
copy paste bugs. This could reduce debugability and could be reverted.
- This touches `delaunay_2d.cc` and the intersection code. I would like
to know @howardt opinion on the matter.
- The `noexcept` on the copy constructor of `mpq(2|3)` is being removed.
But according to @JacquesLucke it is not a real problem for now.

I would like to give a huge thanks to @JacquesLucke who helped during this
and pushed me to reduce the duplication further.

Reviewed By: brecht, sergey, JacquesLucke

Differential Revision: https://developer.blender.org/D13791
2022-01-12 12:57:07 +01:00
fb6bd88644 Revert "BLI: Refactor vector types & functions to use templates"
Includes unwanted changes

This reverts commit 46e049d0ce.
2022-01-12 12:50:02 +01:00
Clment Foucault
46e049d0ce BLI: Refactor vector types & functions to use templates
This patch implements the vector types (i.e:`float2`) by making heavy
usage of templating. All vector functions are now outside of the vector
classes (inside the `blender::math` namespace) and are not vector size
dependent for the most part.

In the ongoing effort to make shaders less GL centric, we are aiming
to share more code between GLSL and C++ to avoid code duplication.

####Motivations:
 - We are aiming to share UBO and SSBO structures between GLSL and C++.
 This means we will use many of the existing vector types and others
 we currently don't have (uintX, intX). All these variations were
 asking for many more code duplication.
 - Deduplicate existing code which is duplicated for each vector size.
 - We also want to share small functions. Which means that vector
 functions should be static and not in the class namespace.
 - Reduce friction to use these types in new projects due to their
 incompleteness.
 - The current state of the `BLI_(float|double|mpq)(2|3|4).hh` is a
 bit of a let down. Most clases are incomplete, out of sync with each
 others with different codestyles, and some functions that should be
 static are not (i.e: `float3::reflect()`).

####Upsides:
 - Still support `.x, .y, .z, .w` for readability.
 - Compact, readable and easilly extendable.
 - All of the vector functions are available for all the vectors types
 and can be restricted to certain types. Also template specialization
 let us define exception for special class (like mpq).
 - With optimization ON, the compiler unroll the loops and performance
 is the same.

####Downsides:
 - Might impact debugability. Though I would arge that the bugs are
 rarelly caused by the vector class itself (since the operations are
 quite trivial) but by the type conversions.
 - Might impact compile time. I did not saw a significant impact since
 the usage is not really widespread.
 - Functions needs to be rewritten to support arbitrary vector length.
 For instance, one can't call `len_squared_v3v3` in
 `math::length_squared()` and call it a day.
 - Type cast does not work with the template version of the `math::`
 vector functions. Meaning you need to manually cast `float *` and
 `(float *)[3]` to `float3` for the function calls.
 i.e: `math::distance_squared(float3(nearest.co), positions[i]);`
 - Some parts might loose in readability:
 `float3::dot(v1.normalized(), v2.normalized())`
 becoming
 `math::dot(math::normalize(v1), math::normalize(v2))`
 But I propose, when appropriate, to use
 `using namespace blender::math;` on function local or file scope to
 increase readability.
 `dot(normalize(v1), normalize(v2))`

####Consideration:
 - Include back `.length()` method. It is quite handy and is more C++
 oriented.
 - I considered the GLM library as a candidate for replacement. It felt
 like too much for what we need and would be difficult to extend / modify
 to our needs.
 - I used Macros to reduce code in operators declaration and potential
 copy paste bugs. This could reduce debugability and could be reverted.
 - This touches `delaunay_2d.cc` and the intersection code. I would like
 to know @howardt opinion on the matter.
 - The `noexcept` on the copy constructor of `mpq(2|3)` is being removed.
 But according to @JacquesLucke it is not a real problem for now.

I would like to give a huge thanks to @JacquesLucke who helped during this
and pushed me to reduce the duplication further.

Reviewed By: brecht, sergey, JacquesLucke

Differential Revision: https://developer.blender.org/D13791
2022-01-12 12:47:43 +01:00
e5766752d0 Revert "BLI: Refactor vector types & functions to use templates"
Reverted because the commit removes a lot of commits.

This reverts commit a2c1c368af.
2022-01-12 12:44:26 +01:00
a2c1c368af BLI: Refactor vector types & functions to use templates
This patch implements the vector types (i.e:float2) by making heavy
usage of templating. All vector functions are now outside of the vector
classes (inside the blender::math namespace) and are not vector size
dependent for the most part.

In the ongoing effort to make shaders less GL centric, we are aiming
to share more code between GLSL and C++ to avoid code duplication.

Motivations:
- We are aiming to share UBO and SSBO structures between GLSL and C++.
  This means we will use many of the existing vector types and others we
  currently don't have (uintX, intX). All these variations were asking
  for many more code duplication.
- Deduplicate existing code which is duplicated for each vector size.
- We also want to share small functions. Which means that vector functions
  should be static and not in the class namespace.
- Reduce friction to use these types in new projects due to their
  incompleteness.
- The current state of the BLI_(float|double|mpq)(2|3|4).hh is a bit of a
  let down. Most clases are incomplete, out of sync with each others with
  different codestyles, and some functions that should be static are not
  (i.e: float3::reflect()).

Upsides:
- Still support .x, .y, .z, .w for readability.
- Compact, readable and easilly extendable.
- All of the vector functions are available for all the vectors types and
  can be restricted to certain types. Also template specialization let us
  define exception for special class (like mpq).
- With optimization ON, the compiler unroll the loops and performance is
  the same.

Downsides:
- Might impact debugability. Though I would arge that the bugs are rarelly
  caused by the vector class itself (since the operations are quite trivial)
  but by the type conversions.
- Might impact compile time. I did not saw a significant impact since the
  usage is not really widespread.
- Functions needs to be rewritten to support arbitrary vector length. For
  instance, one can't call len_squared_v3v3 in math::length_squared() and
  call it a day.
- Type cast does not work with the template version of the math:: vector
  functions. Meaning you need to manually cast float * and (float *)[3] to
  float3 for the function calls.
  i.e: math::distance_squared(float3(nearest.co), positions[i]);
- Some parts might loose in readability:
  float3::dot(v1.normalized(), v2.normalized())
  becoming
  math::dot(math::normalize(v1), math::normalize(v2))
  But I propose, when appropriate, to use
  using namespace blender::math; on function local or file scope to
  increase readability. dot(normalize(v1), normalize(v2))

Consideration:
- Include back .length() method. It is quite handy and is more C++
  oriented.
- I considered the GLM library as a candidate for replacement.
  It felt like too much for what we need and would be difficult to
  extend / modify to our needs.
- I used Macros to reduce code in operators declaration and potential
  copy paste bugs. This could reduce debugability and could be reverted.
- This touches delaunay_2d.cc and the intersection code. I would like to
  know @Howard Trickey (howardt) opinion on the matter.
- The noexcept on the copy constructor of mpq(2|3) is being removed.
  But according to @Jacques Lucke (JacquesLucke) it is not a real problem
  for now.

I would like to give a huge thanks to @Jacques Lucke (JacquesLucke) who
helped during this and pushed me to reduce the duplication further.

Reviewed By: brecht, sergey, JacquesLucke

Differential Revision: http://developer.blender.org/D13791
2022-01-12 12:19:39 +01:00
9d3264b4fd Cleanup: clang-tidy modernize-redundant-void-arg 2021-12-29 18:51:10 -05:00
9e365069af Cleanup: move public doc-strings into headers for 'blenlib'
- Added space below non doc-string comments to make it clear
  these aren't comments for the symbols directly below them.
- Use doxy sections for some headers.
- Minor improvements to doc-strings.

Ref T92709
2021-12-09 20:01:44 +11:00
c1279768a7 Cleanup: Clang-Tidy modernize-redundant-void-arg 2021-12-08 00:31:20 -05:00
c26011efcb Fix T92962 Boolean output indices unstable.
A parallel loop to create the interesection meshes for each triangle
meant that with parallelism, the output order of the created meshes
could vary with each execution. Keep the parallelism for doing the CDTs
for interesection, but move the extraction of the new faces into a
serial loop afterwards, for repeatability.
2021-11-24 15:26:12 -05:00
c5a13ffcb4 Cleanup: spelling in comments 2021-10-18 12:13:10 +11:00
1bfa9539d3 Fix T91889 Exact boolean sometimes drops triangles.
The problem is that the fast triangulator (based on polyfill)
sometimes makes degenerate triangles. Commit 8115f0c5bd91f had
a check for degenerate triangles but it wasn't thorough enough.
This commit uses a more thorough (and pessimistic) test for
degenerate triangles, using the exact triangulator in those cases.
2021-10-10 19:54:02 -04:00
3c3669894f Cleanup: use system includes 2021-10-04 13:14:58 +11:00
1cf45fe10f Cleanup: spelling 2021-08-02 15:22:54 +10:00
3e4c98429b Cleanup: fix clang-tidy readability-else-after-return
No functional changes
2021-07-20 17:11:29 +02:00
3c8d261557 Greatly improve speed of Delaunay when have a lot of holes.
Using part of a patch from Erik Abrahamsson, this replaces the
use of linked lists for original id tracking by Sets.
I had thought that the lists were unlikely to grow to more than
a few elements, but when the mesh has a lot of holes (whose
original ids go *outside* the hole, and therefore, most of the
mesh), this assumption can be very wrong.
On a Text regression test, the time went from 11.67s to 0.16s
with this fix. I also tested to make sure that Boolean didn't
slow down with this, and found it actually had a very slight speedup.

Using Sets exposed a dependency on the ordering of the items
in the id lists, luckily caught by a mesh intersect regression test,
so fixed that.
2021-07-18 10:48:57 -04:00
ceff86aafe Various Exact Boolean parallelizations and optimizations.
From patch D11780 from Erik Abrahamsson.
It parallelizes making the vertices, destruction of map entries,
finding if the result is PWN, finding triangle adjacencies,
and finding the ambient cell.
The latter needs a parallel_reduce from tbb, so added one into
BLI_task.hh so that if WITH_TBB is false, the code will still work.

On Erik's 6-core machine, the elapsed time went from 17.5s to 11.8s
(33% faster) on an intersection of two spheres with 3.1M faces.
On Howard's 24-core machine, the elapsed time went from 18.7s to 10.8s
for the same test.
2021-07-05 18:09:36 -04:00
b8115f0c5b Fix performance regression in Exact boolean due to exact triangulation.
Went back to using Blender's polyfill for triangulation, which is much
faster (time for a 3.1M face boolean went from 103s to 48s).
Had to put in detection for the case that needs the exact triangulator
(bug T86805), and also a fix for non-convex quads (bug T89330).
2021-07-05 10:00:29 -04:00
bd0de99b52 Cleanup: spelling, punctuation 2021-07-05 22:27:03 +10:00
9b89de2571 Cleanup: consistent use of tags: NOTE/TODO/FIXME/XXX
Also use doxy style function reference `#` prefix chars when
referencing identifiers.
2021-07-04 00:43:40 +10:00
1d8648b13a Cleanup: repeated terms in code comments & error messages 2021-06-28 15:46:08 +10:00
7223a0348f Fix T89330 Exact Boolean fails on a simple model.
The problem was an optimization I put in to triangulate quads.
It was wrong if the quad, after projecting onto a 2d plane, was
not convex. Handling quads the same as other faces fixes the bug.
Unfortunately, this will slow down Exact Boolean when the input has
many quads (the usual case, of course).
Will attempt to fix that with a later change, but for now, this
at least restores correctness.
2021-06-26 17:49:52 -04:00
4b9ff3cd42 Cleanup: comment blocks, trailing space in comments 2021-06-24 15:59:34 +10:00
8e43ef5f31 Exact Boolean: speed up when there are many separate components.
Use bounding box tests quickly tell that two components cannot
have a containment relation between each other. This change
cut about 0.6s off a test with 25 big icospheres.
2021-06-05 11:31:08 -07:00
8180d478e1 Speedup exact boolean by avoiding some mallocs and frees.
This is from patch D11432 from Erik Abrahamsson. He found that
in some mpq3 functions called frequently from loops, passing in
buffers for termporary mpq3 values can save substantial time.
On my machine, his example in that patch went from 9.48s to 7.50s
for the boolean part of the calculation. On his machine, a running
time went from 17s to 10.3s.
2021-05-31 17:03:48 -04:00
ee8593fe76 Cleanup: clang-tidy 2021-05-03 10:23:15 +02:00
28bf1d4037 Fix T87554 Exact Boolean performance bug.
There was a quadratic algorithm extracting triangles from a coplanar
cluster. This is now linear.
Also found and fixed a bug in the same area related to the triangulator
added recently: it didn't get the right correspondence between new
edges and original edges.
2021-05-02 16:37:05 -04:00
19dfb6ea1f Cleanup: enable modernize-use-equals-default check
This removes a lot of unnecessary code that is generated by
the compiler automatically.

In very few cases, a defaulted destructor in a .cc file is
still necessary, because of forward declarations in the header.

I removed some defaulted virtual destructors, because they are not
necessary, when the parent class has a virtual destructor already.

Defaulted constructors are only necessary when there is another
constructor, but the class should still be default constructible.

Differential Revision: https://developer.blender.org/D10911
2021-04-08 11:07:27 +02:00
7054d03701 Cleanup: Clang-tidy modernize-use-default-member-init
Using assignment syntax as we don't use `{}` initialization yet.

Reviewed By: sergey
Differential Revision: https://developer.blender.org/D9501
2021-02-05 19:09:36 +05:30
17e1e2bfd8 Cleanup: correct spelling in comments 2021-02-05 16:23:34 +11:00
a90504303e Reorder fields in boolean's ITT_value to save memory. 2020-12-06 10:58:14 -05:00
8982a315b7 Add more timing hooks for boolean. 2020-12-05 07:48:41 -05:00
246c11634f Speedups for new boolean. Better hash function for verts.
The existing hash function didn't work well with Set's method of
masking to the lower bits, because many verts have zeros in the
lower bits.
Also, replaced VectorSet with Set for Vert deduping.
2020-11-23 19:30:40 -05:00
af013ff76f Cleanup: clang-tidy 2020-11-16 21:54:28 +11:00
52a189936b Merge branch 'blender-v2.91-release'
Bring in exact boolean fix.
2020-11-15 20:26:14 -05:00
fbffff26e4 Fix T82736, Exact Boolean fail with repeated subtraction of same object.
Two problems were fixed. One, the code for dissolving vertices
left a face around if dissolving a vertex would leave less than
three vertices. Instead, the face should be deleted.
Two, with transformations like "rotate 180 degrees", this should
be no problem with exact, but the current transformation matrix
has very small non-zero entries where it shouldn't. Cleaning the
transformation matrix makes it more likely that user expectations
about coplanar faces will be fulfilled.
2020-11-15 20:24:59 -05:00
6507449e54 Cleanup: fix wrong merge, remove extra unique_ptr.
Mistakes added in 3cb4c51308 and
bec1765340

Reviewed By: sergey

Differential Revision: https://developer.blender.org/D9514
2020-11-09 19:32:16 +05:30
525a042c5c Cleanup: fix some clang tidy issues 2020-11-09 12:05:07 +01:00
bec1765340 Merge new boolean fix from blender-v2.91-release. 2020-11-07 09:33:56 -05:00
46da8e9eb9 Fix T82301, exact boolean fail on cube with bump.
The code for determining coplanar clusters had a bug where it would
miss some triangles. The fix for now is to just put triangles in
the cluster if their bounding boxes overlap. This works but maybe
makes clusters bigger then they have to be. I'll follow this commit
with work on making the CDT routine faster when using exact arithmetic.
Also removed a lot of unused code, and added some new intersect
performance tests.
2020-11-07 09:02:58 -05:00
16732def37 Cleanup: Clang-Tidy modernize-use-nullptr
Replace `NULL` with `nullptr` in C++ code.

No functional changes.
2020-11-06 18:08:25 +01:00
3cb4c51308 Cleanup: Clang-Tidy, modernize-make-unique 2020-11-06 16:47:16 +01:00
190170d4cc Cleanup: Clang-Tidy, readability-redundant-member-init 2020-11-06 11:54:53 +01:00
aa3a4973a3 Cleanup: use ELEM macro 2020-11-06 12:32:54 +11:00
c249eb7a8d Fix new boolean performance bug.
The code that decided to use a faster double version of plane
side testing forgot to take an absolute value, so half the time
the exact code was being used when it was unnecessary.
2020-10-31 17:21:18 -04:00
30826a5e49 Fix new boolean performance bug.
The code that decided to use a faster double version of plane
side testing forgot to take an absolute value, so half the time
the exact code was being used when it was unnecessary.
2020-10-31 16:46:11 -04:00
da6e6e0432 New boolean: Fix second example in T79404.
The code to detect non-trivial coplanar intersection sometimes
falsely said there wasn't one. This caused some coplanar intersections
to be missed. Also added a test for this case.
2020-09-04 20:59:36 -04:00
19363880a6 New boolean: silence an "unused" warning.
Previous commit stopped using some functions. Since I may need
them again for future performance tuning, these are just ifdef'd out
for now.
2020-08-30 14:11:36 -04:00
19c9b27ffe New boolean: another performance improvement.
Instead of calculating exact normals for all faces, just do it
for those that potentially intersect. A big improvement for dense
meshes that only intersect in relatively few places.
2020-08-30 13:47:18 -04:00
3789aa8506 New Boolean: performance improvement.
Avoided cost of searching for coplanar clusters in many cases.
2020-08-29 17:48:01 -04:00
d8585e184a New boolean: fixed a bug in coplanar intersect.
The code that found coplanar clusters was not updating a bounding box.
Also, code that was detecting non-trivial coplanar intersects was
slightly wrong, but that would not have caused any functional problems.
2020-08-29 11:31:47 -04:00