discuss@lists.openscad.org

OpenSCAD general discussion Mailing-list

View all threads

Cannot Difference Multiple Module Instances

NS
Nathan Sokalski
Fri, Aug 18, 2023 4:34 AM

I am attempting to use difference() to subtract 2 instances of a module for another instance of the module. It works fine when subtracting only one instance, but subtracting 2 does not work. For example:

//The following works fine:
difference(){
      MyModule();//Instance One
      MyModule();}//Instance Two
//The following works fine:
difference(){
      MyModule();//Instance One
      MyModule();}//Instance Three
//The following does not work:
difference(){
      MyModule();//Instance One
      MyModule();//Instance Two
      MyModule();}//Instance Three

The last of the above examples gives the following output:

Compiling design (CSG Tree generation)...

Compiling design (CSG Products generation)...

Geometries in cache: 1277

Geometry cache size in bytes: 14822752

CGAL Polyhedrons in cache: 6

CGAL cache size in bytes: 93491736

Compiling design (CSG Products normalization)...

WARNING: Normalized tree is growing past 200000 elements. Aborting normalization.

WARNING: CSG normalization resulted in an empty tree

Normalized tree has 0 elements!

Compile and preview finished.

Total rendering time: 0:00:00.209

I'm not sure how to figure out what the problem is, since all the instances work individually, and can be subtracted individually. What should I do?

Nathan Sokalski
njsokalski@hotmail.commailto:njsokalski@hotmail.com

I am attempting to use difference() to subtract 2 instances of a module for another instance of the module. It works fine when subtracting only one instance, but subtracting 2 does not work. For example: //The following works fine: difference(){       MyModule();//Instance One       MyModule();}//Instance Two //The following works fine: difference(){       MyModule();//Instance One       MyModule();}//Instance Three //The following does not work: difference(){       MyModule();//Instance One       MyModule();//Instance Two       MyModule();}//Instance Three The last of the above examples gives the following output: Compiling design (CSG Tree generation)... Compiling design (CSG Products generation)... Geometries in cache: 1277 Geometry cache size in bytes: 14822752 CGAL Polyhedrons in cache: 6 CGAL cache size in bytes: 93491736 Compiling design (CSG Products normalization)... WARNING: Normalized tree is growing past 200000 elements. Aborting normalization. WARNING: CSG normalization resulted in an empty tree Normalized tree has 0 elements! Compile and preview finished. Total rendering time: 0:00:00.209 I'm not sure how to figure out what the problem is, since all the instances work individually, and can be subtracted individually. What should I do? Nathan Sokalski njsokalski@hotmail.com<mailto:njsokalski@hotmail.com>
M
mikeonenine@web.de
Fri, Aug 18, 2023 5:16 AM

Nathan Sokalski wrote:

//The following does not work:
difference(){
      MyModule();//Instance One
      MyModule();//Instance Two
      MyModule();}//Instance Three

Don’t quite see the point in subtracting MyModule from MyModule, but

difference()

{
      module one();
      module two();
      module three();

}

Subtracts two and three from one. If you want to subtract three from one and two, it needs a union:

difference()

{

union()

{
      module one();
      module two();

}
      module three();

}

Nathan Sokalski wrote: > > //The following does not work: > difference(){ >       MyModule();//Instance One >       MyModule();//Instance Two >       MyModule();}//Instance Three Don’t quite see the point in subtracting MyModule from MyModule, but difference() { \       module one();\       module two();\       module three(); } Subtracts two and three from one. If you want to subtract three from one and two, it needs a union: difference() { union() {\       module one();\       module two(); }\       module three(); }
NS
Nathan Sokalski
Fri, Aug 18, 2023 5:57 AM

Sorry for the misunderstanding, what I submitted was just to show that I was using difference (my actual modules are obviously much more complex & have multiple parameters, so the instances would not all be the same like in my post). The problem I am having only occurs when I am subtracting 2 elements (which is why the difference() that does not work is the one with 3 children)

Nathan Sokalski
njsokalski@hotmail.commailto:njsokalski@hotmail.com


From: mikeonenine@web.de mikeonenine@web.de
Sent: Friday, August 18, 2023 1:16 AM
To: discuss@lists.openscad.org discuss@lists.openscad.org
Subject: [OpenSCAD] Re: Cannot Difference Multiple Module Instances

Nathan Sokalski wrote:

//The following does not work: difference(){       MyModule();//Instance One       MyModule();//Instance Two       MyModule();}//Instance Three

Don’t quite see the point in subtracting MyModule from MyModule, but

difference()

{
      module one();
      module two();
      module three();

}

Subtracts two and three from one. If you want to subtract three from one and two, it needs a union:

difference()

{

union()

{
      module one();
      module two();

}
      module three();

}

Sorry for the misunderstanding, what I submitted was just to show that I was using difference (my actual modules are obviously much more complex & have multiple parameters, so the instances would not all be the same like in my post). The problem I am having only occurs when I am subtracting 2 elements (which is why the difference() that does not work is the one with 3 children) Nathan Sokalski njsokalski@hotmail.com<mailto:njsokalski@hotmail.com> ________________________________ From: mikeonenine@web.de <mikeonenine@web.de> Sent: Friday, August 18, 2023 1:16 AM To: discuss@lists.openscad.org <discuss@lists.openscad.org> Subject: [OpenSCAD] Re: Cannot Difference Multiple Module Instances Nathan Sokalski wrote: //The following does not work: difference(){       MyModule();//Instance One       MyModule();//Instance Two       MyModule();}//Instance Three Don’t quite see the point in subtracting MyModule from MyModule, but difference() {       module one();       module two();       module three(); } Subtracts two and three from one. If you want to subtract three from one and two, it needs a union: difference() { union() {       module one();       module two(); }       module three(); }
GH
gene heskett
Fri, Aug 18, 2023 7:36 AM

On 8/18/23 00:35, Nathan Sokalski wrote:

I am attempting to use difference() to subtract 2 instances of a module
for another instance of the module. It works fine when subtracting only
one instance, but subtracting 2 does not work. For example:

//The following works fine:
difference(){
      MyModule();//Instance One
      MyModule();}//Instance Two
//The following works fine:
difference(){
      MyModule();//Instance One
      MyModule();}//Instance Three
//The following does not work:
difference(){
      MyModule();//Instance One
      MyModule();//Instance Two
      MyModule();}//Instance Three

The last of the above examples gives the following output:

Compiling design (CSG Tree generation)...

Compiling design (CSG Products generation)...

Geometries in cache: 1277

Geometry cache size in bytes: 14822752

CGAL Polyhedrons in cache: 6

CGAL cache size in bytes: 93491736

Compiling design (CSG Products normalization)...

WARNING: Normalized tree is growing past 200000 elements. Aborting
normalization.

WARNING: CSG normalization resulted in an empty tree

Normalized tree has 0 elements!

Compile and preview finished.

Total rendering time: 0:00:00.209

I'm not sure how to figure out what the problem is, since all the
instances work individually, and can be subtracted individually. What
should I do?

Nathan Sokalski
njsokalski@hotmail.com mailto:njsokalski@hotmail.com

Nathan: In edit>preferences>advanced, you need to set bigger buffers.
Some of this can use huge amounts of memory. I'm doing even more complex
stuff and I've set buffers to use the 32G's in this machine. If your box
doesn't have the memory it can use swap but swap gets slow. I'm set for
100G of swap.  I'm also using the latest AppImage in linux, available
from the far bottom of the home page, much faster that the 2 yo release.

Cheers, Gene Heskett.

"There are four boxes to be used in defense of liberty:
soap, ballot, jury, and ammo. Please use in that order."
-Ed Howdershelt (Author, 1940)
If we desire respect for the law, we must first make the law respectable.

On 8/18/23 00:35, Nathan Sokalski wrote: > I am attempting to use difference() to subtract 2 instances of a module > for another instance of the module. It works fine when subtracting only > one instance, but subtracting 2 does not work. For example: > > //The following works fine: > difference(){ >       MyModule();//Instance One >       MyModule();}//Instance Two > //The following works fine: > difference(){ >       MyModule();//Instance One >       MyModule();}//Instance Three > //The following does not work: > difference(){ >       MyModule();//Instance One >       MyModule();//Instance Two >       MyModule();}//Instance Three > > The last of the above examples gives the following output: > > Compiling design (CSG Tree generation)... > > Compiling design (CSG Products generation)... > > Geometries in cache: 1277 > > Geometry cache size in bytes: 14822752 > > CGAL Polyhedrons in cache: 6 > > CGAL cache size in bytes: 93491736 > > Compiling design (CSG Products normalization)... > > WARNING: Normalized tree is growing past 200000 elements. Aborting > normalization. > > WARNING: CSG normalization resulted in an empty tree > > Normalized tree has 0 elements! > > Compile and preview finished. > > Total rendering time: 0:00:00.209 > > > I'm not sure how to figure out what the problem is, since all the > instances work individually, and can be subtracted individually. What > should I do? > > Nathan Sokalski > njsokalski@hotmail.com <mailto:njsokalski@hotmail.com> > Nathan: In edit>preferences>advanced, you need to set bigger buffers. Some of this can use huge amounts of memory. I'm doing even more complex stuff and I've set buffers to use the 32G's in this machine. If your box doesn't have the memory it can use swap but swap gets slow. I'm set for 100G of swap. I'm also using the latest AppImage in linux, available from the far bottom of the home page, much faster that the 2 yo release. Cheers, Gene Heskett. -- "There are four boxes to be used in defense of liberty: soap, ballot, jury, and ammo. Please use in that order." -Ed Howdershelt (Author, 1940) If we desire respect for the law, we must first make the law respectable. - Louis D. Brandeis Genes Web page <http://geneslinuxbox.net:6309/>
JB
Jordan Brown
Fri, Aug 18, 2023 4:24 PM

On 8/17/2023 9:34 PM, Nathan Sokalski wrote:

WARNING: Normalized tree is growing past 200000 elements. Aborting
normalization. 

On its face, OpenSCAD is complaining that your model is too complex.  Is
it a complex model?  Try making it less complex, to see if that makes
the problem go away.  (I understand that it likely as complex as it
needs to be, but for diagnostic purposes try stripping stuff out.)

When you preview one instance of your module, how many nodes are in the
tree?  Look for

Normalized tree has 2 elements! 

in the console pane.  Does the number make sense for what you're trying
to do?  If it reports you have thousands of nodes, and you know that you
have thousands of individual pieces, fine, but if you think you only
have a handful of pieces but it reports thousands, maybe there's a bug.

Is the number in the high tens of thousands?  With a limit of 200,000,
three modules with more than ~66K nodes each would exceed the limit.

Can you share the program?

On 8/17/2023 9:34 PM, Nathan Sokalski wrote: > > WARNING: Normalized tree is growing past 200000 elements. Aborting > normalization.  > On its face, OpenSCAD is complaining that your model is too complex.  Is it a complex model?  Try making it less complex, to see if that makes the problem go away.  (I understand that it likely as complex as it needs to be, but for diagnostic purposes try stripping stuff out.) When you preview one instance of your module, how many nodes are in the tree?  Look for Normalized tree has 2 elements! in the console pane.  Does the number make sense for what you're trying to do?  If it reports you have thousands of nodes, and you know that you have thousands of individual pieces, fine, but if you think you only have a handful of pieces but it reports thousands, maybe there's a bug. Is the number in the high tens of thousands?  With a limit of 200,000, three modules with more than ~66K nodes each would exceed the limit. Can you share the program?
HL
Hans L
Fri, Aug 18, 2023 6:05 PM

On Thu, Aug 17, 2023, 11:35 PM Nathan Sokalski njsokalski@hotmail.com
wrote:

WARNING: Normalized tree is growing past 200000 elements. Aborting
normalization.

WARNING: CSG normalization resulted in an empty tree

First things first, you can go to Preferences -> Advanced -> Turn off
rendering at _____ elements, and increase the value there.
The limit is meant to help curb exploding memory usage under certain
circumstances, but if you have the memory for it then it doesn't hurt to
add a zero or two.

What this means: OpenCSG requires the boolean geometry expression to be in
a "Sum of Products" form aka disjunctive normal form (DNF).
That's what the "Design" -> "Display CSG Products" menu entry refers to,
and you can see how that goes together.  Converting an arbitrary boolean
expression to DNF, in the worst case, can balloon to 2^N terms.
Where N is the number of geometry nodes originally in the CSG Tree.
This is loosely related to the well known computer science problem of
Boolean Satisfiability (SAT) which is NP hard.

There is also some mention of the issue in this FAQ entry:
https://en.wikibooks.org/wiki/OpenSCAD_User_Manual/FAQ#Why_is_the_preview_so_slow
?

To reduce these number of terms you can wrap some of your inner nested
boolean operations in render() { ... }
This effectively will convert that subtree of operations into a single
geometry leaf node, which simplifies the normalization stage of preview.
This will cause preview to take some extra time initially, but will greatly
help the draw times (per frame, when orbiting camera etc.).
It is best to do this on parts involving boolean operations, which have low
to medium geometry complexity, but are possibly repeated often in the
overall composition.

Hope that helps.

On Thu, Aug 17, 2023, 11:35 PM Nathan Sokalski <njsokalski@hotmail.com> wrote: > WARNING: Normalized tree is growing past 200000 elements. Aborting > normalization. > > WARNING: CSG normalization resulted in an empty tree > First things first, you can go to Preferences -> Advanced -> Turn off rendering at _____ elements, and increase the value there. The limit is meant to help curb exploding memory usage under certain circumstances, but if you have the memory for it then it doesn't hurt to add a zero or two. What this means: OpenCSG requires the boolean geometry expression to be in a "Sum of Products" form aka disjunctive normal form (DNF). That's what the "Design" -> "Display CSG Products" menu entry refers to, and you can see how that goes together. Converting an arbitrary boolean expression to DNF, in the worst case, can balloon to 2^N terms. Where N is the number of geometry nodes originally in the CSG Tree. This is loosely related to the well known computer science problem of Boolean Satisfiability (SAT) which is NP hard. There is also some mention of the issue in this FAQ entry: https://en.wikibooks.org/wiki/OpenSCAD_User_Manual/FAQ#Why_is_the_preview_so_slow ? To reduce these number of terms you can wrap some of your inner nested boolean operations in render() { ... } This effectively will convert that subtree of operations into a single geometry leaf node, which simplifies the normalization stage of preview. This will cause preview to take some extra time initially, but will greatly help the draw times (per frame, when orbiting camera etc.). It is best to do this on parts involving boolean operations, which have low to medium geometry complexity, but are possibly repeated often in the overall composition. Hope that helps.