Shape sharing and save-restore

Here's the place for discussion related to coding in FreeCAD, C++ or Python. Design, interfaces and structures.
Forum rules
Be nice to others! Respect the FreeCAD code of conduct!
User avatar
tanderson69
Veteran
Posts: 1626
Joined: Thu Feb 18, 2010 1:07 am

Re: Merging of my Link branch

Post by tanderson69 »

DeepSOIC wrote: Fri Aug 03, 2018 10:19 am Although changing OCC to store shape sharing is a better way in the long run.. and maybe it even does so already... I experimented with it quite long ago, things may have changed.
the occt shape sharing works great as long as all the shapes are wrote to the same brep file. Think... 'aggregate TopoDS_Compound'. I tested and proved this out about 5 years ago. Juergen didn't seem very interested, when I brought it up. I am doing it successfully in another project, so believe me it works.
User avatar
DeepSOIC
Veteran
Posts: 7896
Joined: Fri Aug 29, 2014 12:45 am
Location: used to be Saint-Petersburg, Russia

Re: Merging of my Link branch

Post by DeepSOIC »

this is getting off-topic, but...

tanderson69 wrote: Fri Aug 03, 2018 1:07 pm the occt shape sharing works great as long as all the shapes are wrote to the same brep file. Think... 'aggregate TopoDS_Compound'. I tested and proved this out about 5 years ago. Juergen didn't seem very interested, when I brought it up. I am doing it successfully in another project, so believe me it works.
I'm afraid I can't reproduce it.

I create Lattice2 Polar array, and run to test if there is sharing:

Code: Select all

sh = App.ActiveDocument.PolarArray.Shape
sh.Shells[0].isPartner(sh.Shells[1]) # shells are paper planes, should be a one shell used many times...
After array creation/recompute:

Code: Select all

>>> sh = App.ActiveDocument.PolarArray.Shape
>>> sh.Shells[0].isPartner(sh.Shells[1])
True
and after save/load:

Code: Select all

>>> sh = App.ActiveDocument.PolarArray.Shape
>>> sh.Shells[0].isPartner(sh.Shells[1])
False
>>> 
OS: Windows 10
Word size of OS: 64-bit
Word size of FreeCAD: 64-bit
Version: 0.18.13935 (Git)
Build type: Release
Branch: master
Hash: cb133767464337e4b5c8589a1fe33b4d7dad7721
Python version: 2.7.14
Qt version: 4.8.7
Coin version: 4.0.0a
OCC version: 7.2.0
Locale: Russian/RussianFederation (ru_RU)
User avatar
DeepSOIC
Veteran
Posts: 7896
Joined: Fri Aug 29, 2014 12:45 am
Location: used to be Saint-Petersburg, Russia

Shape sharing and save-restore

Post by DeepSOIC »

tanderson69 wrote: Fri Aug 03, 2018 1:07 pm I am doing it successfully in another project, so believe me it works.
DeepSOIC wrote: Fri Aug 03, 2018 2:23 pm I'm afraid I can't reproduce it.
Any ideas on what the difference might be? I've glanced through the source you sent me in PM, and I don't straight see anything special. Does it write a binary brep, or an ascii one?
User avatar
tanderson69
Veteran
Posts: 1626
Joined: Thu Feb 18, 2010 1:07 am

Re: Shape sharing and save-restore

Post by tanderson69 »

DeepSOIC wrote: Fri Aug 03, 2018 10:29 pm Any ideas on what the difference might be?
No. I was thinking about doing some more experiments, but haven't fit it in yet.


DeepSOIC wrote: Fri Aug 03, 2018 10:29 pmDoes it write a binary brep, or an ascii one?
Those are ascii. you have to get into the occt bintools for binary.https://dev.opencascade.org/doc/refman/ ... tools.html
chrisb
Veteran
Posts: 53923
Joined: Tue Mar 17, 2015 9:14 am

Re: Shape sharing and save-restore

Post by chrisb »

I moved some topics here on request of DeepSOIC. Please verify it were the right ones.
A Sketcher Lecture with in-depth information is available in English, auf Deutsch, en français, en español.
realthunder
Veteran
Posts: 2190
Joined: Tue Jan 03, 2017 10:55 am

Re: Merging of my Link branch

Post by realthunder »

DeepSOIC wrote: Fri Aug 03, 2018 2:23 pm this is getting off-topic, but...

tanderson69 wrote: Fri Aug 03, 2018 1:07 pm the occt shape sharing works great as long as all the shapes are wrote to the same brep file. Think... 'aggregate TopoDS_Compound'. I tested and proved this out about 5 years ago. Juergen didn't seem very interested, when I brought it up. I am doing it successfully in another project, so believe me it works.
I'm afraid I can't reproduce it.
This is because PropertyTopoShape performs a copy before saving, which seems to be a deep copy and destroys the shape sharing. I have just submitted a PR for this. See the description for details.

It is indeed like what tanderson69 said, the maximum efficiency can be achieved by storing all shapes inside one file. But then, the same thing can be achieved, to some extent, if my Link gets wildly used :D , which BTW, your Lattice seems a perfect use case.

Storing all shapes into one file has an disadvantage, though. My branch now supports partial document loading when externally linked, meaning only the referenced shapes gets loaded. Storing all shapes in one file kind of defeats its purpose.
Try Assembly3 with my custom build of FreeCAD at here.
And if you'd like to show your support, you can donate through patreon, liberapay, or paypal
User avatar
DeepSOIC
Veteran
Posts: 7896
Joined: Fri Aug 29, 2014 12:45 am
Location: used to be Saint-Petersburg, Russia

Re: Shape sharing and save-restore

Post by DeepSOIC »

realthunder wrote: Sat Aug 04, 2018 6:39 am This is because PropertyTopoShape performs a copy before saving, which seems to be a deep copy and destroys the shape sharing. I have just submitted a PR for this. See the description for details.
Oh, nice!!
User avatar
DeepSOIC
Veteran
Posts: 7896
Joined: Fri Aug 29, 2014 12:45 am
Location: used to be Saint-Petersburg, Russia

Re: Shape sharing and save-restore

Post by DeepSOIC »

chrisb wrote: Sat Aug 04, 2018 6:34 am I moved some topics here on request of DeepSOIC. Please verify it were the right ones.
thanks!
User avatar
tanderson69
Veteran
Posts: 1626
Joined: Thu Feb 18, 2010 1:07 am

Re: Merging of my Link branch

Post by tanderson69 »

realthunder wrote: Sat Aug 04, 2018 6:39 amThis is because PropertyTopoShape performs a copy before saving, which seems to be a deep copy and destroys the shape sharing. I have just submitted a PR
In regards to the pull request: The link you posted is for writing binary tools. Doesn't FreeCAD saves in the ascii format? Seems like 'BRepTools::Write' saves the triangulation. It looks like at one time the original shape was getting cleaned and that was leading to problems. So a copy was added. By the way, I think the call to BRepTools::Clean now is redundant. BRepBuilderAPI_Copy will only copy the triangulation with the appropriate parameter. https://dev.opencascade.org/doc/refman/ ... _copy.html


realthunder wrote: Sat Aug 04, 2018 6:39 am Storing all shapes into one file has an disadvantage, though. My branch now supports partial document loading when externally linked, meaning only the referenced shapes gets loaded. Storing all shapes in one file kind of defeats its purpose.
I have had the same thought, but then I think if I can share all that data across features and components why would I need to partial load the brep. I think the sharing is one occt greatest strengths, if they can track down all the bugs it causes.

I have been pondering partial loading for a while. I have designed some pretty descent sized assemblies with less than 1 gig of ram, so I appreciate what it can do for you. I just feel that with every passing year, partial loading gets less and less important. I know! dangerous/lazy thinking. There will always be assemblies that won't fit into memory.
User avatar
tanderson69
Veteran
Posts: 1626
Joined: Thu Feb 18, 2010 1:07 am

Re: Shape sharing and save-restore

Post by tanderson69 »

Did an experiment this morning. If you look at the code for 'BRepTools::Write' it isn't really doing anything other using BRepTools::ShapeSet https://git.dev.opencascade.org/gitweb/ ... =HEAD#l689 BRepTools::ShapeSet has a parameter for storing with triangles. So I created a quick test that writes out 2 files directly using BRepTools::ShapeSet. If you diff the results, it looks like this will work. This way we won't have to 'clean' the shapes before write. Should save the sharing and also be a little faster. The more time I spend thinking about this, I feel the shapes should just be all wrote out in binary. Especially if all the shapes will be saved into a giant compound. Why are we saving in ascii?

Code: Select all

#include <iostream>
#include <sstream>
#include <string>
#include <vector>
#include <stdexcept>
#include <fstream>

#include <BRepPrimAPI_MakeBox.hxx>
#include <BRepMesh_IncrementalMesh.hxx>
#include <TopoDS_Solid.hxx>
#include <BRepTools.hxx>
#include <BRepTools_ShapeSet.hxx>


int main (int /*argc*/, char** /*argv*/)
{
  try
  {
    TopoDS_Solid box = BRepPrimAPI_MakeBox(gp_Pnt(0.0, 0.0, 0.0), gp_Pnt(10.0, 10.0, 10.0)).Solid();
    BRepMesh_IncrementalMesh(box, 0.25);
    
    std::ofstream withStream("./withTriangles.brep", std::ios_base::out | std::ios_base::trunc);
    BRepTools_ShapeSet withSet(Standard_True); //this is the default
    withSet.Add(box);
    withSet.Write(withStream);
    withSet.Write(box, withStream);
    
    std::ofstream withOutStream("./withOutTriangles.brep", std::ios_base::out | std::ios_base::trunc);
    BRepTools_ShapeSet withOutSet(Standard_False);
    withOutSet.Add(box);
    withOutSet.Write(withOutStream);
    withOutSet.Write(box, withOutStream);

    std::cout << std::endl << "Program finished normally" << std::endl;
  }
  catch (const Standard_Failure &error)
  {
    std::cout << "OCC Error: " << error.GetMessageString() << std::endl;
  }
  catch (const std::exception &error)
  {
    std::cout << "My Error: " << error.what() << std::endl;
  }

  return 0;
}
Attachments
withTriangles.brep
(3.67 KiB) Downloaded 32 times
withOutTriangles.brep
(2.49 KiB) Downloaded 41 times
Post Reply