Store edges or faces as properties for scripted objects.

Need help, or want to share a macro? Post here!
Forum rules
Be nice to others! Respect the FreeCAD code of conduct!
TheMarkster
Veteran
Posts: 5505
Joined: Thu Apr 05, 2018 1:53 am

Re: Store edges or faces as properties for scripted objects.

Post by TheMarkster »

josegegas wrote: Fri Dec 03, 2021 1:01 am
Then, the user selects two edges or faces belonging to the same object, and I do:

Code: Select all

fp.reference_1 = (FreeCADGui.Selection.getSelection()[0],FreeCADGui.Selection.getSelectionEx()[0].SubElementNames[0])
fp.reference_2 = (FreeCADGui.Selection.getSelection()[0],FreeCADGui.Selection.getSelectionEx()[0].SubElementNames[1])
This works well so far, but now I want to recover the center of mass of reference_1 and of reference_2 (which can be edges or faces), and I'm not sure how to do so. Any ideas?
What means "recover"? To get the center of mass, just enter:

Code: Select all

face.CenterOfMass

edge.CenterOfMass
josegegas
Posts: 241
Joined: Sat Feb 11, 2017 12:54 am
Location: New Zealand

Re: Store edges or faces as properties for scripted objects.

Post by josegegas »

TheMarkster wrote: Fri Dec 03, 2021 5:54 pm
josegegas wrote: Fri Dec 03, 2021 1:01 am
Then, the user selects two edges or faces belonging to the same object, and I do:

Code: Select all

fp.reference_1 = (FreeCADGui.Selection.getSelection()[0],FreeCADGui.Selection.getSelectionEx()[0].SubElementNames[0])
fp.reference_2 = (FreeCADGui.Selection.getSelection()[0],FreeCADGui.Selection.getSelectionEx()[0].SubElementNames[1])
This works well so far, but now I want to recover the center of mass of reference_1 and of reference_2 (which can be edges or faces), and I'm not sure how to do so. Any ideas?
What means "recover"? To get the center of mass, just enter:

Code: Select all

face.CenterOfMass
edge.CenterOfMass
The object has reference_1 and reference_2. How can I get the center of mass out of these? Of course I cannot simply do

Code: Select all

reference_1.CenterIfMass 


I need to do something to get the edges or faces out of reference_1 and reference_2...

By doing:

Code: Select all

 fp.reference_1[0]
I get:

Code: Select all

<Part::PartFeature>
Which is the whole shape selected by the user (FreeCADGui.Selection.getSelection()[0]).

And:

Code: Select all

 fp.reference_1[1]
returns:

Code: Select all

['Edge10']
Where "Edge10" is a string. So the question is, how can I get the edge named 'Edge10' out of <Part::PartFeature>? I´ve been looking for some method like Part.GetEdgesByName() or similar, but no luck so far...
User avatar
Chris_G
Veteran
Posts: 2579
Joined: Tue Dec 31, 2013 4:10 pm
Location: France
Contact:

Re: Store edges or faces as properties for scripted objects.

Post by Chris_G »

Code: Select all

theShape = fp.reference_1[0].Shape
firstEdge = theShape.getElement(fp.reference_1[1][0])
User avatar
onekk
Veteran
Posts: 6144
Joined: Sat Jan 17, 2015 7:48 am
Contact:

Re: Store edges or faces as properties for scripted objects.

Post by onekk »

Probably, the OP, whant to make something like.
  1. Store an object shape () in his case only some edges that e want to modify
  2. operate on the shape, modifying it as needed
  3. have the ability to "recover" the original shape
  4. apply new modification to the old shape
Or similar thing, like storing some "position" on the original shape and apply modification to the same positions, when as example a dims is changes.

He was speaking of joints, I have in mind some like you want to model say a rod and apply some modification to an edge, but if the rod is changed (maybe modify only the length or the diameter), store edges and apply modification to "same" edges of the new object.

In this case, the problem is to determine a proper position as edge number could change.

For this a simple object in my opinion is not sufficient.

You have to script a whole new object class that could build and object and store "joints position" in a manner that it could survive some shape modifications, in other word, even if it is a simple "tube" you have to store "building parameters" and "joints positions" and rebuild the whole object if something is changed.

This is derived from the analysis of the code he posted:

Code: Select all

class Revolutepin:
    def __init__(self, obj, label, node, reference1, reference2):      
...
He is storing reference1 and reference2 as a way to retrieve the "joint positions" based on "edge number" on the original shape.

maybe using some mean to store a relative position in respect of the center of mass, wil make something useful, but the shapes should be simple shapes, where some reference like "N", "NE" or similar could have sense.

if you think of doing some joints to a rod that is a cylinder, and then modify the rod shape to a "hexagonal rod" you could have some idea, the edge count is very different, but some "N", "S", "E", "W" positions could have a logical mean.

Different thing would be if you want to generalize things, and use maybe a figure similar to the image posted, where maybe if this something that resemble a "modified cube" with six faces, maybe slanted it could have even a sense, but if you modify a face to have say a protrusion, edge count and position is not helping a lot.

So a sort of abstraction or categories of shapes has to be done to have a mean to have a "predictable joint position" when altering "base shape", simply storing edge reference will not be enough.

Hoping have not guessed things wrong.

Regards


Carlo D.
GitHub page: https://github.com/onekk/freecad-doc.
- In deep articles on FreeCAD.
- Learning how to model with scripting.
- Various other stuffs.

Blog: https://okkmkblog.wordpress.com/
TheMarkster
Veteran
Posts: 5505
Joined: Thu Apr 05, 2018 1:53 am

Re: Store edges or faces as properties for scripted objects.

Post by TheMarkster »

(untested)

Code: Select all

obj = reference_1[0]
elements = reference_1[1]
edges = [obj.getSubObject(element) for element in elements if "Edge" in element]
faces =  [obj.getSubObject(element) for element in elements if "Face" in element]
josegegas
Posts: 241
Joined: Sat Feb 11, 2017 12:54 am
Location: New Zealand

Re: Store edges or faces as properties for scripted objects.

Post by josegegas »

thanks a lot for the responses!

I now understand how to use App::PropertyLinkSubList, and I have already modified a couple of my joint classes to make them fully parametric, and it works like a charm!

phpBB [video]
paullee
Veteran
Posts: 5097
Joined: Wed May 04, 2016 3:58 pm

Re: Store edges or faces as properties for scripted objects.

Post by paullee »

Looks Great !
Post Reply