[Solved] Gui.Selection.getSelectionEx() problem

Need help, or want to share a macro? Post here!
Forum rules
Be nice to others! Respect the FreeCAD code of conduct!
Post Reply
jfc4120
Posts: 448
Joined: Sat Jul 02, 2022 11:16 pm

[Solved] Gui.Selection.getSelectionEx() problem

Post by jfc4120 »

Code: Select all

OS: Windows 10 Version 2009
Word size of FreeCAD: 64-bit
Version: 0.20.29177 (Git)
Build type: Release
Branch: releases/FreeCAD-0-20
Hash: 68e337670e227889217652ddac593c93b5e8dc94
Python 3.8.10, Qt 5.15.2, Coin 4.0.1, Vtk 8.2.0, OCC 7.6.2
Locale: English/United States (en_US)
Installed mods: 
  * Help 1.0.3

I am just learning getSelectionEx and am experimenting.

Image included. If I select the one labeled 1 I get:

Code: Select all

18:41:12  (Vector (-292.7307434082031, -731.577392578125, 0.0),)
18:41:12  -292.7307434082031
18:41:12  -11.524832200978944
Selecting end of the line 2, I get:

Code: Select all

18:41:12  (Vector (-292.7307434082031, -731.577392578125, 0.0),)
18:41:12  -292.7307434082031
18:41:12  -11.524832200978944
18:42:53  (Vector (-273.8681335449219, -738.897216796875, 0.0),)
18:42:53  -273.8681335449219
18:42:53  -10.782209779377991
However if I select the point labeled 3, I get an error:
18:44:27 Traceback (most recent call last):
File "C:/Users/Owner/AppData/Roaming/FreeCAD/Macro/Get_Line_two.FCMacro", line 9, in <module>
sels[0].SubObjects[0].ShapeType
<class 'IndexError'>: tuple index out of range
Note I only selected the point. Is this a bug? Seems you cannot select just a point if added to the end of a line without problems.
Even though the line is not in or part of the selection.

Small test script:

Code: Select all

# -*- coding: utf-8 -*-

import FreeCAD,FreeCADGui
import Draft
import math
from PySide import QtGui

sels = Gui.Selection.getSelectionEx()
sels[0].SubObjects[0].ShapeType
PT = sels[0].SubObjects[0].Point

PX= sels[0].PickedPoints

print(PX)

X1 = PX[0].x
print(PX[0].x)
X1 = X1 *  .039370078

print(X1)
Edit:

I tried combinations of getSelection() also, but could not find an example that worked. Tried:

Code: Select all

# -*- coding: utf-8 -*-

import FreeCAD,FreeCADGui
import Draft
import math
from PySide import QtGui

s = FreeCADGui.Selection.getSelection()
PX=s[0].Shape

print(PX[0].x)
Got:
19:27:55 Traceback (most recent call last):
File "C:/Users/Owner/AppData/Roaming/FreeCAD/Macro/Get_single.FCMacro", line 11, in <module>
print(PX[0].x)
<class 'TypeError'>: 'Part.Wire' object is not subscriptable
Attachments
sel.png
sel.png (4.72 KiB) Viewed 1078 times
sel2.png
sel2.png (41.85 KiB) Viewed 1078 times
Last edited by jfc4120 on Thu Jul 28, 2022 3:36 am, edited 2 times in total.
edwilliams16
Veteran
Posts: 3191
Joined: Thu Sep 24, 2020 10:31 pm
Location: Hawaii
Contact:

Re: Gui.Selection.getSelectionEx() problem

Post by edwilliams16 »

jfc4120 wrote: Wed Jul 27, 2022 11:50 pm
However if I select the point labeled 3, I get an error:
18:44:27 Traceback (most recent call last):
File "C:/Users/Owner/AppData/Roaming/FreeCAD/Macro/Get_Line_two.FCMacro", line 9, in <module>
sels[0].SubObjects[0].ShapeType
<class 'IndexError'>: tuple index out of range

The error message is an index is out of range. If it is sels[0] out of range, you failed to select anything. If it is SubObjects[0], then we know that the attribute exists (SubObjects) or we would have got an non-existent attribute error. So that says the SubObjects list is empty.
You can test for this with sels[0].HasSubObjects

Why would be list be empty? - likely you picked the entire object (two clicks, or from the tree). This is all a bit academic with a single point object, but say for a cube, you could have selected a single vertex or edge or the entire cube. In the last case there are no sub-objects. In the first two the SubObject tells you what bit of the cube you selected. ( or bits if you multiple- selected subobjects eg a vertex and a face of the same object)
jfc4120
Posts: 448
Joined: Sat Jul 02, 2022 11:16 pm

Re: Gui.Selection.getSelectionEx() problem

Post by jfc4120 »

I only selected one point.

Selecting the one labeled one works selecting the end of the line works, however selecting one point that's at the intersection of the other lines labeled three or trying to select one that's on a line gives error.

Also I have tried three more times same results. The point is definitely selected. Not the lines also but just the point.

Also that is not the end of a line it's an actual point I placed there.

But I will test as you suggest, what do I put in the print?
jfc4120
Posts: 448
Joined: Sat Jul 02, 2022 11:16 pm

Re: Gui.Selection.getSelectionEx() problem

Post by jfc4120 »

Tested:

1. point only: true
2. not point, but end of the line: true
3. point on line (not line end), only point is selected: error

Code: Select all

# -*- coding: utf-8 -*-

import FreeCAD,FreeCADGui
import Draft
import math
from PySide import QtGui

sels = Gui.Selection.getSelectionEx()
sels[0].SubObjects[0].ShapeType
print(sels[0].HasSubObjects)
#PT = sels[0].SubObjects[0].Point

#PX= sels[0].PickedPoints

#print(PX)

#X1 = PX[0].x
#print(PX[0].x)
#X1 = X1 *  .039370078

#print(X1)
Attachments
true
true
t1.png (41.92 KiB) Viewed 973 times
true
true
t2.png (49.5 KiB) Viewed 973 times
error
error
t3.png (43.53 KiB) Viewed 973 times
edwilliams16
Veteran
Posts: 3191
Joined: Thu Sep 24, 2020 10:31 pm
Location: Hawaii
Contact:

Re: Gui.Selection.getSelectionEx() problem

Post by edwilliams16 »

Include the file, or you force me to keep guessing.

EDIT
Try this

Code: Select all

sel = Gui.Selection.getSelectionEx()[0]
if sel.HasSubObjects:
    v = sel.SubObjects[0]
    if v.ShapeType == 'Vertex':
        print(f'SubObject[0] is Vertex at {v.Point}')
    else:
        print(f'SubObject[0] is a {v.ShapeType}')
else:
    v = sel.Object.Shape
    if v.ShapeType == 'Vertex':
        print(f'Object is Vertex at {v.Point}')
    else:
        print(f'Object is a {v.ShapeType}')

which will tell you what you are selecting.
jfc4120
Posts: 448
Joined: Sat Jul 02, 2022 11:16 pm

Re: Gui.Selection.getSelectionEx() problem

Post by jfc4120 »

A simple one attached with same results.

Edit results:

Code: Select all

21:42:50  SubObject[0] is Vertex at Vector (-41.25200653076172, 10.353130340576172, 0.0)
21:43:09  SubObject[0] is Vertex at Vector (-29.37399673461914, 23.836278915405273, 0.0)
21:43:21  Object is Vertex at Vector (-7.54414176940918, 24.638843536376953, 0.0)
Chosen in same order.

First point.
second line end.
third point on line end.

Edir2:

I tested this:

Code: Select all

# -*- coding: utf-8 -*-

import FreeCAD,FreeCADGui
import Draft
import math
from PySide import QtGui
sel = Gui.Selection.getSelectionEx()[0]
if sel.HasSubObjects:
    v = sel.SubObjects[0]
    if v.ShapeType == 'Vertex':
        print(f'SubObject[0] is Vertex at {v.Point}')
    else:
        print(f'SubObject[0] is a {v.ShapeType}')
else:
    v = sel.Object.Shape
    if v.ShapeType == 'Vertex':
        print(f'Object is Vertex at {v.Point}')
        X1 = v.Point.x *  .039370078             ########  HERE
        print(X1)                                 ########  HERE
    else:
        print(f'Object is a {v.ShapeType}')
And that works. Thank you, it's very hard being new to find that type of information. Believe me I searched a lot first.

I still don't understand this:
Object is Vertex at Vector (-7.54414176940918, 24.638843536376953, 0.0)
When it's also a regular point. Point001 in drawing.

I also noticed if a point is on a line, you cannot select it with mouse, you have to select with name in left panel.

I still need to check how this works with a named point, I'll try that tomorrow.
Attachments
point_line.FCStd
(7.33 KiB) Downloaded 11 times
Last edited by jfc4120 on Thu Jul 28, 2022 3:09 am, edited 1 time in total.
edwilliams16
Veteran
Posts: 3191
Joined: Thu Sep 24, 2020 10:31 pm
Location: Hawaii
Contact:

Re: Gui.Selection.getSelectionEx() problem

Post by edwilliams16 »

jfc4120 wrote: Thu Jul 28, 2022 2:40 am

Code: Select all

21:43:21  Object is Vertex at Vector (-7.54414176940918, 24.638843536376953, 0.0)
Only way I can get this is selecting Point001 in the tree view. When picking that point, I had to hide Line001, or I ended up picking the end of the line instead. In any case, look in the status bar and/or the python console to verify you picked what you think you picked.

But what is is the problem? The code I gave you works whether the point shows up as the picked object or its sub-object.
jfc4120
Posts: 448
Joined: Sat Jul 02, 2022 11:16 pm

Re: Gui.Selection.getSelectionEx() problem

Post by jfc4120 »

Yes it works.

To add, I once used autocad, so far freecad is a steeper learning curve. But fun so far.

The kicker: autocad 10 (not 2010), 10.
edwilliams16
Veteran
Posts: 3191
Joined: Thu Sep 24, 2020 10:31 pm
Location: Hawaii
Contact:

Re: Gui.Selection.getSelectionEx() problem

Post by edwilliams16 »

jfc4120 wrote: Thu Jul 28, 2022 3:24 am
Everything in the tree view is a Document Object. When you select in the tree view, you select the entire object - say a cube.

Code: Select all

sel = Gui.Selection.getSelectionEx()[0]
sel.Object is the object. If it is some geometrical object (not say a spreadsheet), it has a Shape , sel.Object.Shape. If you explore the shape, you can find its topology - Vertexes, Edges, Faces etc. However, it won't be obvious which Vertex is which. Select one in the 3D view and its name will be in the status bar - Vertex1 is Vertexes[0] (because python numbers from zero) etc.

If you select in the 3D view, say some Edges and/or Vertices FreeCAD knows which ones you picked and puts them in sel.SubObjects

When the entire object is just a single point, for consistency, it behaves just the same way, depending on whether you selected it in the tree view or the 3D view.

A very useful tool is to do Ctl-shift-P after making a selection. You'll get something like

Code: Select all

>>> doc = App.getDocument("point_line")
>>> obj = doc.getObject("Line")
>>> shp = obj.Shape
>>> sub = obj.getSubObject("Edge1")
>>> ### End command Std_SendToPythonConsole
in the Python console. You can then do command completion on the results ( doc, obj, shp, sub)
to dig out the Properties or methods you need.
Post Reply