Moving a rotated Part in Global XYZ

Need help, or want to share a macro? Post here!
Forum rules
Be nice to others! Respect the FreeCAD code of conduct!
User avatar
onekk
Veteran
Posts: 6098
Joined: Sat Jan 17, 2015 7:48 am
Contact:

Re: Moving a rotated Part in Global XYZ

Post by onekk »

You could try to inspect sources, doing something like "grep -nR "getCursorPos" ./Mod/ " in the appropriate directory of FreeCAD sources.
a simple search lead to this use in

/Mod/Draft/draftguitools/gui_dimensions.py around line 591:

Code: Select all

cursor = active_view.getCursorPos()
cursor_point = active_view.getPoint(cursor)
self.point = plane.projectPoint(cursor_point)
it seems that there is a manner to retrieve the correct 3d coordinates, but I haven't tried a real code.

In this files it appears that there are some helpers methods to cope with Coin3D and drawing coordinates.

./Mod/Draft/draftguitools/gui_tool_utils.py


Hope it could help.

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/
freedman
Veteran
Posts: 3415
Joined: Thu Mar 22, 2018 3:02 am
Location: Washington State, USA

Re: Moving a rotated Part in Global XYZ

Post by freedman »

I found what I need with some google searching, at least for the XY axis. Here is some code that rotates coords XY to a new XY by angle.

Code: Select all

	self.point = (3, 4)
        self.origin = (2, 2)
        self.angle = math.radians(10)
 
    def rotate_sub(self,origin, point, angle):  #  Rotate a point counterclockwise by a given angle (in radians) around a given origin..
        ox, oy = origin
        px, py = point
    
        qx = ox + math.cos(angle) * (px - ox) - math.sin(angle) * (py - oy)
        qy = oy + math.sin(angle) * (px - ox) + math.cos(angle) * (py - oy)
        return qx, qy 
So to move a rotated Part in the global XY I add all the rotations of the parent Parts and do a (360- total_parent_angles= offset_angle). Feed my coords and angle offset to the function and out comes my XY in the Global XY. It works great!


The way I move stuff:
Since everything has to be in a Part, when I click on a object I store it's name and it's Part coords as an offset. Then I use this:
"self.listObjects = FreeCADGui.ActiveDocument.ActiveView.getObjectsInfo(v.getCursorPos(),0)"
I look thru the listObjects and find the Name of the object I clicked on or use a default, in the listObjects are the coords of the object (under the cursor), as the cursor moves the listObjects reports new coords and I make that the new Placement. This moves the Part relative to the mouse.

onekk, thanks.
User avatar
onekk
Veteran
Posts: 6098
Joined: Sat Jan 17, 2015 7:48 am
Contact:

Re: Moving a rotated Part in Global XYZ

Post by onekk »

Ok this is not a problem, to calculate points on 2D you can always use the "translation of axes", problems arise when you do it in 3D.

However in FreeCAD sources I'm almost sure that there is less involute way to do it, but as usual, it's a well hidden secret in "clear view".

To be more precise, if you know vector math there will be no problem to rotate things, if you don't have a good mathematical education, you will revert to use "simple math", I have used this way many times, for example to calculate vertexes of regular polygon or to obtain angle between two lines (in 2D space), as FreeCAD has some methods, but are taylored to to things differently and sometimes give some "counter intuitive" results (from my mathematically impaired mind ) :-D.

a side note, I hope that your angle is in radians as python math.sin and math.cos expect angles in radians:
# Return the sine value of 30 degrees
print(math.sin(math.radians(30)))

# Return the sine value of 90 degrees
print(math.sin(math.radians(90)))
My former post was an answer to the way to obtain the 3D coordinates having the mouse positions, as used in some FreeCAD sources I've found.

If you are speaking of Sketches, there is no problem, I hope if you are using the normal convention that sketches are in the XY plane, but I fear that is possible to have sketches in other planes (maybe a remember wrong) so it has to be checked if your math is working also for a sketch as example in XZ or YZ plane.

If the formulas are for your "personal use only" no problem, as you know that your math works in XY plane and when obtained the wires, you could rotate them as you need, but for example if they are to be put in a Macro, it is another story.

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/
freedman
Veteran
Posts: 3415
Joined: Thu Mar 22, 2018 3:02 am
Location: Washington State, USA

Re: Moving a rotated Part in Global XYZ

Post by freedman »

Here is a link to what I started about a year ago.
https://forum.freecadweb.org/viewtopic. ... im#p365829
Because it's a world like simulation there is always a need for ground under the model to base where items sit, kind of like what gravity would do. This works well to base objects always sitting on something because Z is stable and only changes when stuff sits on stuff or following terrain.
I have solved many problems with the SIM macro and this Part rotation thing was one my last major issues, I hope. I certainly have improved my Python. I hope to release something soon.
I can do complex math but I have little time so I mostly need to copy stuff.
User avatar
onekk
Veteran
Posts: 6098
Joined: Sat Jan 17, 2015 7:48 am
Contact:

Re: Moving a rotated Part in Global XYZ

Post by onekk »

What is the problem, sorry i don't guess well.

Maybe to obtain the orientation of the ground?

I think, but I've not tried anything similar, that you could extract the point on surface and for this point extract the curve and for the curve extract the curvature and the tangent, and work on this data, problem is as your example seem to show that you have to do this taking in account the path that you want to follow (Images seem to show two vehicles that go from point A to point B, and having the wheels on the ground.).

Maybe I've guessed totally wrong yout problem, sorry for that.

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/
edwilliams16
Veteran
Posts: 3080
Joined: Thu Sep 24, 2020 10:31 pm
Location: Hawaii
Contact:

Re: Moving a rotated Part in Global XYZ

Post by edwilliams16 »

freedman
Veteran
Posts: 3415
Joined: Thu Mar 22, 2018 3:02 am
Location: Washington State, USA

Re: Moving a rotated Part in Global XYZ

Post by freedman »

Thanks edwilliams an onekk
That write-up by ickby really states how Part needs to be handled.
I have what I need to move on.
edwilliams16
Veteran
Posts: 3080
Joined: Thu Sep 24, 2020 10:31 pm
Location: Hawaii
Contact:

Re: Moving a rotated Part in Global XYZ

Post by edwilliams16 »

Let me understand better your problem. I think you have the following situation.

At the top level in your document, you have a number of Part containers.
Each Part container can contain objects and/or more Part Containers.

These form a tree.
By clicking on your screen you can identify a particular object in the hierarchy. By manipulating the mouse and/or keyboard, you indicate how you would like to translate or rotate the chosen object in the global coordinate system. You also indicate somehow the depth of objects you wish to move synced with your chosen object.

Level 0 would be just to change the placement of the object within its parent Part, leaving everything else alone. To do this, we need to calculate a new Placement for the object within the Part, given the change in Global Placement.
Level 1 would be to change the placement of the object's parent Part thereby moving all the objects contained within it. To do this we would need to calculate the new Placement of the parent Part Container, given the change in global Placement of our selected object within it.
We can continue this higher and higher up the tree, moving a larger and larger block of objects, moving the parent, the grand-parent etc. and their contents by adjusting the Placement of the ancestor Part.

I don't know how to handle the UI issues, but given the input data (level, desired change in global Placement), I expect to be able to compute the required Placement to effect the change. It's a generalization of ickby's recipe.
freedman
Veteran
Posts: 3415
Joined: Thu Mar 22, 2018 3:02 am
Location: Washington State, USA

Re: Moving a rotated Part in Global XYZ

Post by freedman »

edwilliams16, you nailed that explaination. You can see in the pic two Part assemblies, of coarse they aren't truely constrained assemblies but I can't find a better word. Objects are kind-of constrained in the Z direction because as you drag one object over another they will stack.
I created a new object I call the Center Spire, it's always held at the center of the parent Part so if you rotate the deck for instance, everything will rotate around the spire. I found that without some kind of origin marker (the spire) Parts would get moved all over the fricken place and the rotation center would be a mystery.
I can grab the spire and drag it to move the assemble while using the keyboard to rotate it, it's fun. I haven't explored how far I can go with this concept, parents and grandparents. I can think of some cool stuff but I don't know that I can code it. :)
Attachments
sim22.JPG
sim22.JPG (96.36 KiB) Viewed 865 times
Post Reply