Thank you so much for posting this. i was struggling with this for a while 
and your solution really helped me! I hope this gets implemented into some 
version of pyqtgraph - it works quite well!

m.e.

On Thursday, 19 May 2016 12:05:14 UTC+2, B. Oytun Peksel wrote:
>
> Well I realize now even posting a question makes your understanding 
> boost.I solved the problem couple of hours later. It works very good so far
>
> def mPosition(self):
>         #This function is called by a mouse event
>         ## Get mouse coordinates saved when the mouse is clicked( incase 
> dragging)
>         mx = self._downpos.x()
>         my = self._downpos.y()
>         self.Candidates = [] #Initiate a list for storing indices of 
> picked points
>         #Get height and width of 2D Viewport space
>         view_w = self.width()
>         view_h = self.height()
>         #Convert pixel values to normalized coordinates
>         x = 2.0 * mx / view_w - 1.0
>         y = 1.0 - (2.0 * my / view_h)
>         # Convert projection and view matrix to numpy types and inverse 
> them
>         PMi = self.projectionMatrix().inverted()[0]
>         # PMi = numpy.matrix([PMi[0:4],
>         #                    PMi[4:8],
>         #                    PMi[8:12],
>         #                    PMi[12:16]])
>         VMi = self.viewMatrix().inverted()[0]
>         # VMi = numpy.matrix([VMi[0:4],
>         #                    VMi[4:8],
>         #                    VMi[8:12],
>         #                    VMi[12:16]])
>         #Move to clip coordinates by chosing z= -1 and w 1 (Dont 
> understand this part)
>         # Q1: Why are we picking arbitrary -1 for z?
>         ray_clip = QtGui.QVector4D(x, y, -1.0, 1.0) # get transpose for 
> matrix multiplication
>         # Q2 = Clip space should clip some of the scene depending on the 
> zoom. How is it done? Is it implicit
>         # in the transformation matrices?
>         # Convert to eye space by view matrix
>         ray_eye = PMi * ray_clip
>         ray_eye.setZ(-1)
>         ray_eye.setW(0)
>         #Convert to world coordinates
>         ray_world = VMi * ray_eye
>         ray_world = QtGui.QVector3D(ray_world.x(), ray_world.y(), 
> ray_world.z()) # get transpose for matrix multiplication
>         ray_world.normalize()
>         #ray_world = ray_world / numpy.linalg.norm(ray_world) # normalize 
> to get the ray
>         # Q3: Since we normalize this vector, does it mean the values are 
> a b c values of a ray definition in
>         # linear algebra such as z = ax+by+c
>         # Now I 'll use the ray intersection with spheres. I assume every 
> point is a sphere with a radius
>         #Please see http://antongerdelan.net/opengl/raycasting.html 
> scroll down to spehere intersection
>         O = numpy.matrix(self.cameraPosition())  # camera position should 
> be starting point of the ray
>         ray_world = numpy.matrix([ray_world.x(), ray_world.y(), 
> ray_world.z()])
>         # Q4: Is this approach correct? Is starting point really the 
> camera coordinates obtained like this?
>         print O, ray_world
>         for i, C in enumerate(self.Poss): # Iterate over all points
>             OC = O - C
>             b = numpy.inner(ray_world, OC)
>             b = b.item(0)
>             c = numpy.inner(OC, OC)
>             #Q5: When the plot function is called with pxMode = False the 
> sizes should reflect the size of point
>             #dots in world coordinates. So I assumed they were the 
> diameter of the spheres. Is this correct? Otherwise how do I reach the
>             #diameter of spheres in terms of world coordinates?
>             c = c.item(0) - (self.Sizes[i]/2)**2   
> #numpy.square((self.Sizes[i]))
>             bsqr = numpy.square(b)
>             if (bsqr - c) >= 0: # means intersection
>                 self.Candidates.append(self.GlobalInds[i])
>
>         print self.Candidates
>
>
>
> On Thursday, May 19, 2016 at 9:00:29 AM UTC+2, B. Oytun Peksel wrote:
>>
>> First of all I would like to thank Bi Ge for his/her help. I could not 
>> make it work so I tried to find a different approach to the problem. I 
>> think it is important we have alternatives cause this will be a important 
>> function for pyqtgraph development. 
>>
>> So instead of projecting all points to the 2D viewport space I took the 
>> approach of ray casting and used this page as  reference; 
>> http://antongerdelan.net/opengl/raycasting.html
>>
>> My questions are embedded in the comments in the code as Q1..Q5 in the 
>> method call mPosition. Please scroll down to see it. it is the last method. 
>>
>>
>> from PySide import QtCore, QtGui
>> import pyqtgraph.opengl as gl
>> import numpy
>>
>>
>> class PlotObject(gl.GLViewWidget):
>>     """ Override GLViewWidget with enhanced behavior
>>
>>     """
>>     #: Fired in update() method to synchronize listeners.
>>     #sigUpdate = QtCore.Signal(float, float)
>>     App = None
>>
>>     def __init__(self, app=None):
>>
>>         if self.App is None:
>>             if app is not None:
>>                 self.App = app
>>             else:
>>                 self.App = QtGui.QApplication([])
>>         super(PlotObject,self).__init__()
>>         self.Gridxy = gl.GLGridItem()
>>         self.Gridyz = gl.GLGridItem()
>>         self.Gridxz = gl.GLGridItem()
>>         self.Axes = gl.GLAxisItem()
>>         self.Gridxy.setSize(6000,2000,3)
>>         self.Gridxy.setSpacing(200,200,0)
>>         self.Gridxy.translate(3000, 0, 0)
>>
>>         self.Gridyz.setSize(1800,2000,3)
>>         self.Gridyz.setSpacing(200,200,0)
>>         self.Gridyz.translate(900, 0, 0)
>>         self.Gridyz.rotate(-90, 0, 1, 0)
>>
>>
>>         self.Gridxz.setSize(6000,2000,3)
>>         self.Gridxz.setSpacing(200,200,0)
>>         self.Gridxz.translate(3000, -1000, 0)
>>         self.Gridxz.rotate(-90, 1, 0, 0)
>>         self.Poss = []
>>
>>         self.Plot = gl.GLScatterPlotItem()
>>
>>         self.addItem(self.Plot)
>>         self.addItem(self.Gridxy)
>>         self.addItem(self.Gridyz)
>>         self.addItem(self.Gridxz)
>>         self.addItem(self.Axes)
>>         self._downpos = []
>>
>>         #self.sigUpdate.connect(self.rayCast)
>>         self.setWindowTitle('Center of Gravity of Parts')
>>
>>     def mousePressEvent(self, ev):
>>         """ Store the position of the mouse press for later use.
>>
>>         """
>>         super(PlotObject, self).mousePressEvent(ev)
>>         self._downpos = self.mousePos
>>
>>     def mouseReleaseEvent(self, ev):
>>         """ Allow for single click to move and right click for context 
>> menu.
>>
>>         Also emits a sigUpdate to refresh listeners.
>>         """
>>         super(PlotObject, self).mouseReleaseEvent(ev)
>>         if self._downpos == ev.pos():
>>             x = ev.pos().x()
>>             y = ev.pos().y()
>>             if ev.button() == 2 :
>>                 self.mPosition()
>>             elif ev.button() == 1:
>>                 x = x - self.width() / 2
>>                 y = y - self.height() / 2
>>                 #self.pan(-x, -y, 0, relative=True)
>>                 print self.opts['center']
>>                 print x,y
>>         self._prev_zoom_pos = None
>>         self._prev_pan_pos = None
>>
>>
>>     def mouseMoveEvent(self, ev):
>>         """ Allow Shift to Move and Ctrl to Pan.
>>
>>         """
>>         shift = ev.modifiers() & QtCore.Qt.ShiftModifier
>>         ctrl = ev.modifiers() & QtCore.Qt.ControlModifier
>>         if shift:
>>             y = ev.pos().y()
>>             if not hasattr(self, '_prev_zoom_pos') or not 
>> self._prev_zoom_pos:
>>                 self._prev_zoom_pos = y
>>                 return
>>             dy = y - self._prev_zoom_pos
>>             def delta():
>>                 return -dy * 5
>>             ev.delta = delta
>>             self._prev_zoom_pos = y
>>             self.wheelEvent(ev)
>>         elif ctrl:
>>             pos = ev.pos().x(), ev.pos().y()
>>             if not hasattr(self, '_prev_pan_pos') or not 
>> self._prev_pan_pos:
>>                 self._prev_pan_pos = pos
>>                 return
>>             dx = pos[0] - self._prev_pan_pos[0]
>>             dy = pos[1] - self._prev_pan_pos[1]
>>             self.pan(dx, dy, 0, relative=True)
>>             self._prev_pan_pos = pos
>>         else:
>>             super(PlotObject, self).mouseMoveEvent(ev)
>>     def plotGLPlot(self, objs):
>>         poss = numpy.array([0, 0, 0])
>>         self.Poss = []
>>         self.GlobalInds = []
>>         weights = numpy.array(0, dtype=float)
>>         def pswc (x) : return 10 * x**0.25 #pseudoweight calculation with 
>> exponential scaling
>>         for obj in objs:
>>             for i,cogs in enumerate(obj.CoG):
>>                 for cog in cogs:
>>                     #cog[1] = 0
>>                     if obj.PieceWeight[i]:
>>                         poss = numpy.vstack([poss,numpy.asarray(cog.T)])
>>                         self.Poss.append(numpy.matrix(cog.T)) # for 
>> picking stuff
>>                         self.GlobalInds.append(obj.Index[i])
>>                         pw = pswc(obj.PieceWeight[i])
>>                         weights = numpy.append(weights, pw)
>>
>>
>>
>>         maxw = max(weights)
>>         threshold = numpy.mean(weights)
>>         self.Colors = numpy.empty([len(weights),4])
>>         for i, pw in enumerate(weights):
>>             if pw <= threshold:
>>                 c = pw / maxw
>>                 self.Colors[i] = numpy.array([c,1,0,0.7])
>>             else:
>>                 c = 1 - pw / maxw
>>                 self.Colors[i] = numpy.array([1,c,0,0.7])
>>
>>         self.removeItem(self.Plot)
>>         self.Plot = gl.GLScatterPlotItem()
>>         self.Plot.setData(pos=poss, size=weights, color=self.Colors, 
>> pxMode=False)
>>         self.Sizes = weights
>>         self.addItem(self.Plot)
>>         self.show()
>>
>>     def mPosition(self):
>>         #This function is called by a mouse event
>>         ## Get mouse coordinates saved when the mouse is clicked( incase 
>> dragging)
>>         mx = self._downpos.x()
>>         my = self._downpos.y()
>>         self.Candidates = [] #Initiate a list for storing indices of 
>> picked points
>>         #Get height and width of 2D Viewport space
>>         view_w = self.width()
>>         view_h = self.height()
>>         #Convert pixel values to normalized coordinates
>>         x = 2.0 * mx / view_w - 1.0
>>         y = 1.0 - (2.0 * my / view_h)
>>         # Convert projection and view matrix to numpy types and inverse 
>> them
>>         PM = numpy.matrix([self.projectionMatrix().data()[0:4],
>>                            self.projectionMatrix().data()[4:8],
>>                            self.projectionMatrix().data()[8:12],
>>                            self.projectionMatrix().data()[12:16]])
>>         PMi = numpy.linalg.inv(PM)
>>         VM = numpy.matrix([self.viewMatrix().data()[0:4],
>>                            self.viewMatrix().data()[4:8],
>>                            self.viewMatrix().data()[8:12],
>>                            self.viewMatrix().data()[12:16]])
>>         VMi = numpy.linalg.inv(VM)
>>         #Move to clip coordinates by chosing z= -1 and w 1 (Dont 
>> understand this part)
>>         # Q1: Why are we picking arbitrary -1 for z?
>>         ray_clip = numpy.matrix([x, y, -1.0, 1.0]).T # get transpose for 
>> matrix multiplication
>>         # Q2 = Clip space should clip some of the scene depending on the 
>> zoom. How is it done? Is it implicit
>>         # in the transformation matrices?
>>         # Convert to eye space by view matrix
>>         ray_eye = PMi * ray_clip
>>         ray_eye[2] = -1
>>         ray_eye[3] = 0
>>         #Convert to world coordinates
>>         ray_world = VMi * ray_eye
>>         ray_world = ray_world[0:3].T # get transpose for matrix 
>> multiplication
>>         ray_world = ray_world / numpy.linalg.norm(ray_world) # normalize 
>> to get the ray
>>         # Q3: Since we normalize this vector, does it mean the values 
>> are a b c values of a ray definition in
>>         # linear algebra such as z = ax+by+c
>>         # Now I 'll use the ray intersection with spheres. I assume every 
>> point is a sphere with a radius
>>         #Please see http://antongerdelan.net/opengl/raycasting.html 
>> scroll down to spehere intersection
>>         O = numpy.matrix(self.cameraPosition())  # camera position should 
>> be starting point of the ray
>>         # Q4: Is this approach correct? Is starting point really the 
>> camera coordinates obtained like this?
>>         print O, ray_world
>>         for i, C in enumerate(self.Poss): # Iterate over all points
>>             OC = O - C
>>             b = numpy.inner(ray_world, OC)
>>             b = b.item(0)
>>             c = numpy.inner(OC, OC)
>>             #Q5: When the plot function is called with pxMode = False 
>> the sizes should reflect the size of point
>>             #dots in world coordinates. So I assumed they were the 
>> diameter of the spheres. Is this correct? Otherwise how do I reach the
>>             #diameter of spheres in terms of world coordinates?
>>             c = c.item(0) - numpy.square((self.Sizes[i] / 2 ))
>>             bsqr = numpy.square(b)
>>             if (bsqr - c) >= 0: # means intersection
>>                 self.Candidates.append(self.GlobalInds[i])
>>
>>         print self.Candidates
>>  
>>
>>
>>
>>
>>
>>
>> On Monday, May 16, 2016 at 11:51:22 PM UTC+2, Bi Ge wrote:
>>>
>>> Oops, WorldView is an extended class of opelgl.GLViewWidget, the 
>>> definition is put below at the end of this thread.  
>>>
>>> " It always gives me the same indice wherever I click. " What exactly 
>>> do you mean the same indice? The projection matrix and view matrix simply 
>>> reflects the current position/view of your view point, it has nothing to do 
>>> with where you click. Yes the projected_array shouldn't contain any value 
>>> greater than 1.
>>>
>>> Note I don't own any rights to the WorldView code:
>>>
>>> class WorldView(gl.GLViewWidget):
>>>     def __init__(self, parent=None):
>>>         global ShareWidget
>>>
>>>         if ShareWidget is None:
>>>             # create a dummy widget to allow sharing objects
>>>             # (textures, shaders, etc) between views
>>>             ShareWidget = QtOpenGL.QGLWidget()
>>>
>>>         QtOpenGL.QGLWidget.__init__(self, parent, ShareWidget)
>>>
>>>         self.setFocusPolicy(QtCore.Qt.ClickFocus)
>>>
>>>         self.opts = {
>>>             # will always appear at the center of the widget
>>>             'center': Vector(0, 0, 0),
>>>             # distance of camera from center
>>>             'distance': 10.0,
>>>             # horizontal field of view in degrees
>>>             'fov':  60,
>>>             # camera's angle of elevation in degrees
>>>             'elevation':  30,
>>>             # camera's azimuthal angle in degrees
>>>             # (rotation around z-axis 0 points along x-axis)
>>>             'azimuth': 45,
>>>             # glViewport params; None == whole widget
>>>             'viewport': None,
>>>         }
>>>         self.setBackgroundColor('k')
>>>         self.items = []
>>>         self.noRepeatKeys = [QtCore.Qt.Key_Right, QtCore.Qt.Key_Left,
>>>                              QtCore.Qt.Key_Up, QtCore.Qt.Key_Down,
>>>                              QtCore.Qt.Key_PageUp, 
>>> QtCore.Qt.Key_PageDown]
>>>         self.keysPressed = {}
>>>         self.keyTimer = QtCore.QTimer()
>>>         self.keyTimer.timeout.connect(self.evalKeyState)
>>>
>>>         self.makeCurrent()
>>>
>>>         self.ray = QtGui.QVector3D(0, 0, 0)
>>>         self.select = False
>>>
>>>     def mousePressEvent(self, event):
>>>         print ("Pressed button", event.button(), "at", event.pos())
>>>
>>>         self.mousePos = event.pos()
>>>         if event.button() == 2:
>>>             self.select = True
>>>         else:
>>>             self.select = False
>>>         print (self.itemsAt((self.mousePos.x(), self.mousePos.y(), 3, 
>>> 3)))
>>>
>>>
>>> On Mon, May 16, 2016 at 7:42 AM, B. Oytun Peksel <oytun....@gmail.com> 
>>> wrote:
>>>
>>>> Ok! I understand what you have done now. Apart from one thing. 
>>>>
>>>> w = WorldView()
>>>>
>>>> Don't know what this is and could not find anything googling. When I 
>>>> get projectionMatrix() and ViewMatrix from pyqtgraph.opengl.
>>>> GLViewWidget
>>>> I get the wrong result. It always gives me the same indice wherever I 
>>>> click. projected_array contains values greater than 1 which I assume 
>>>> should 
>>>> not happen.
>>>>
>>>> So the key question is what is WorldView?
>>>>
>>>> On Monday, May 16, 2016 at 11:25:06 AM UTC+2, Bi Ge wrote:
>>>>>
>>>>> b contains the coordinates (positions) of the points you want to 
>>>>> render, i.e. when you call:
>>>>> w = WorldView()
>>>>> sp1 = gl.GLScatterPlotItem(pos=b, size=1)
>>>>> w.addItem(sp1)
>>>>>
>>>>> Inside the for loop I just iterate through every point in b, calculate 
>>>>> their corresponding positions on the screen (stored in projected_array) 
>>>>> using the projection matrix and choose the "selected point" based on 
>>>>> finding the smallest distance between projected point on the screen and 
>>>>> the 
>>>>> pixel clicked by the mouse, thus:
>>>>>         # find distance between mouse and points on screen
>>>>>         projected_array[:, 0] = (projected_array[:, 0] -
>>>>>                                  (mouse_x/view_w))
>>>>>         projected_array[:, 1] = (projected_array[:, 1] -
>>>>>                                  (mouse_y/view_h))
>>>>>         distance_array = np.power(np.power(projected_array[:, 0], 2) +
>>>>>                                   np.power(projected_array[:, 1], 2), 
>>>>> 0.5)
>>>>>
>>>>>         min_index = np.nanargmin(distance_array)
>>>>>
>>>>> On Mon, May 16, 2016 at 3:51 AM, B. Oytun Peksel <oytun....@gmail.com> 
>>>>> wrote:
>>>>>
>>>>>> Thanks for the response! I have one question. I don't understand what 
>>>>>> b is. What do you mean by raw coordinates? Can you explain what you are 
>>>>>> doing inside the for loop?
>>>>>>
>>>>>>
>>>>>> On Thursday, May 12, 2016 at 4:41:47 PM UTC+2, Bi Ge wrote:
>>>>>>
>>>>>>> "
>>>>>>> `
>>>>>>>        # w = WorldView()
>>>>>>>         __WIDTH = 512
>>>>>>>         __HEIGHT = 424
>>>>>>>         m = w.projectionMatrix() * w.viewMatrix()
>>>>>>>         projected_array = np.zeros((__WIDTH * __HEIGHT, 2))
>>>>>>>         view_w = w.width()
>>>>>>>         view_h = w.height()
>>>>>>>         mouse_x = w.mousePos.x()
>>>>>>>         mouse_y = w.mousePos.y()
>>>>>>>         # b array contains the raw coordinates of all the points on 
>>>>>>> screen        
>>>>>>>         for i in xrange(0, __WIDTH, step):
>>>>>>>             for j in xrange(0, __HEIGHT, step):
>>>>>>>                 pt = m.map(QtGui.QVector3D(b[j*__WIDTH+i, 0],
>>>>>>>                                            b[j*__WIDTH+i, 1],
>>>>>>>                                            b[j*__WIDTH+i, 2]))
>>>>>>>                 # origin range [-1, 1]
>>>>>>>                 projected_array[j*__WIDTH+i, 0] = (pt.x() + 1)/2
>>>>>>>                 projected_array[j*__WIDTH+i, 1] = (- pt.y() + 1)/2
>>>>>>>
>>>>>>>
>>>>>>>         projected_array[:, 0] = (projected_array[:, 0] -
>>>>>>>                                  (mouse_x/view_w))
>>>>>>>         projected_array[:, 1] = (projected_array[:, 1] -
>>>>>>>                                  (mouse_y/view_h))
>>>>>>>         distance_array = np.power(np.power(projected_array[:, 0], 2) 
>>>>>>> +
>>>>>>>                                   np.power(projected_array[:, 1], 
>>>>>>> 2), 0.5)
>>>>>>>
>>>>>>>         min_index = np.nanargmin(distance_array)
>>>>>>>         # mark the selected point on screen with a big sphere
>>>>>>>         sp2.setData(pos=b[min_index, :], size=100)
>>>>>>> `
>>>>>>> "
>>>>>>> Should be self-explanatory, we are basically projecting every point 
>>>>>>> onto the screen to see which one is the closest to the mouse (slow; 
>>>>>>> pretty 
>>>>>>> sure OpenGL has built-in way of doing this) let me know if you have any 
>>>>>>> questions.
>>>>>>>
>>>>>>> Bi
>>>>>>>
>>>>>>> On Thu, May 12, 2016 at 6:14 AM, B. Oytun Peksel <
>>>>>>> oytun....@gmail.com> wrote:
>>>>>>>
>>>>>>>> BiGe, can you please post your solution? I am struggling with the 
>>>>>>>> same thing!
>>>>>>>>
>>>>>>>>
>>>>>>>> On Sunday, June 21, 2015 at 7:12:45 AM UTC+2, Bi Ge wrote:
>>>>>>>>>
>>>>>>>>> Found out why my selected point is jumping all around the screen. 
>>>>>>>>>
>>>>>>>>> When applying 
>>>>>>>>> pt = m.map(QtGui.QVector3D(x,y,z)) 
>>>>>>>>> as Luke pointed out the range for x and y is [-1, 1] but unlike 
>>>>>>>>> the mouse position returned by GLViewWidget, (-1, -1) is actually the 
>>>>>>>>> right 
>>>>>>>>> top corner.
>>>>>>>>>
>>>>>>>>> Thanks for all the help.
>>>>>>>>>
>>>>>>>>> Bi
>>>>>>>>>
>>>>>>>>>
>>>>>>>>> On Saturday, June 20, 2015 at 10:23:16 PM UTC-4, Bi Ge wrote:
>>>>>>>>>>
>>>>>>>>>> I am trying to select a point already in the plot. It is true 
>>>>>>>>>> that I only have the relative x and y axes but from my minimal 
>>>>>>>>>> computer 
>>>>>>>>>> graphics experience I assume I can either a) construct a ray based 
>>>>>>>>>> on the 
>>>>>>>>>> view and camera position and do a poor-man's collision detection to 
>>>>>>>>>> find 
>>>>>>>>>> out which point is closest to that ray. b) convert all points in the 
>>>>>>>>>> scene 
>>>>>>>>>> to 2D based on view and camera position and select the point closed 
>>>>>>>>>> to the 
>>>>>>>>>> mouse.
>>>>>>>>>>
>>>>>>>>>> Of course we will run into situations where two points in 3D 
>>>>>>>>>> overlay in 2D but we are always going to select the point closer to 
>>>>>>>>>> the 
>>>>>>>>>> camera.
>>>>>>>>>>
>>>>>>>>>> Hopefully this cleared my question a bit. 
>>>>>>>>>>
>>>>>>>>>> Bi
>>>>>>>>>>
>>>>>>>>>> On Saturday, June 20, 2015 at 9:30:31 PM UTC-4, Mathew Schwartz 
>>>>>>>>>> wrote:
>>>>>>>>>>>
>>>>>>>>>>> Can you explain a bit more of what you want? If you dont want to 
>>>>>>>>>>> select a point already in the plot, how do you pick a 3d point on a 
>>>>>>>>>>> 2d 
>>>>>>>>>>> screen, there is a third axis that you need to define how deep you 
>>>>>>>>>>> want to 
>>>>>>>>>>> select.
>>>>>>>>>>>
>>>>>>>>>>> On Fri, Jun 19, 2015 at 10:02 AM, Bi Ge <sean...@gmail.com> 
>>>>>>>>>>> wrote:
>>>>>>>>>>>
>>>>>>>>>>>> I've tried itemsAt but it only returns the GLScatterPlotItem 
>>>>>>>>>>>> object instead of a point.
>>>>>>>>>>>>
>>>>>>>>>>>> Bi
>>>>>>>>>>>>
>>>>>>>>>>>> On Thursday, June 18, 2015 at 8:57:37 PM UTC-4, Mathew Schwartz 
>>>>>>>>>>>> wrote:
>>>>>>>>>>>>>
>>>>>>>>>>>>> Im not exactly sure on your questions so I wont try to answer 
>>>>>>>>>>>>> them, but if you are trying to pick a point, there is a method 
>>>>>>>>>>>>> available 
>>>>>>>>>>>>> for that already, itemsAt 
>>>>>>>>>>>>> http://www.pyqtgraph.org/documentation/3dgraphics/glviewwidget.html
>>>>>>>>>>>>>
>>>>>>>>>>>>> In that case, you dont need the 3d vector (its most likely a 
>>>>>>>>>>>>> vector because it needs to point into the screen) just the 2d xy 
>>>>>>>>>>>>> coordinates
>>>>>>>>>>>>>
>>>>>>>>>>>>> On Fri, Jun 19, 2015 at 6:35 AM, Bi Ge <sean...@gmail.com> 
>>>>>>>>>>>>> wrote:
>>>>>>>>>>>>>
>>>>>>>>>>>>>> Hi folks,
>>>>>>>>>>>>>>
>>>>>>>>>>>>>> I would like to pick a point in a 3D scatter plot. I read 
>>>>>>>>>>>>>> from Luke's post here:
>>>>>>>>>>>>>>
>>>>>>>>>>>>>> "
>>>>>>>>>>>>>> This version also has methods for determining the projection 
>>>>>>>>>>>>>> and view matrices, which allows you to determine the 
>>>>>>>>>>>>>> relationship between 
>>>>>>>>>>>>>> 3D and 2D manually:
>>>>>>>>>>>>>>
>>>>>>>>>>>>>> m = glView.projectionMatrix() * glView.viewMatrix()
>>>>>>>>>>>>>>
>>>>>>>>>>>>>> # Map 3D location to normalized device coordaintes: (-1,-1) 
>>>>>>>>>>>>>> and (1,1) are opposite corners of the view
>>>>>>>>>>>>>> pt = m.map(QtGui.QVector3D(x,y,z))
>>>>>>>>>>>>>>
>>>>>>>>>>>>>> # Inverse mapping:
>>>>>>>>>>>>>> pt = m.inverted()[0].map(QtGui.QVector3D(x,y,z))
>>>>>>>>>>>>>>
>>>>>>>>>>>>>>
>>>>>>>>>>>>>> " 
>>>>>>>>>>>>>>
>>>>>>>>>>>>>> My questions are:
>>>>>>>>>>>>>> 1. Does inverse mapping meaning from 2D to 3D? If so, why 
>>>>>>>>>>>>>> does the map take a 3D vector when the point on screen is only 
>>>>>>>>>>>>>> 2D:
>>>>>>>>>>>>>>
>>>>>>>>>>>>>> 2. After apply inverse mapping on a point on the screen, we 
>>>>>>>>>>>>>> get a point(vector) in 3D and from here I just need to cast a 
>>>>>>>>>>>>>> ray and find 
>>>>>>>>>>>>>> where it hits the point I want to find correct?
>>>>>>>>>>>>>>
>>>>>>>>>>>>>> Bi
>>>>>>>>>>>>>>
>>>>>>>>>>>>>> -- 
>>>>>>>>>>>>>> You received this message because you are subscribed to the 
>>>>>>>>>>>>>> Google Groups "pyqtgraph" group.
>>>>>>>>>>>>>> To unsubscribe from this group and stop receiving emails from 
>>>>>>>>>>>>>> it, send an email to pyqtgraph+...@googlegroups.com.
>>>>>>>>>>>>>> To view this discussion on the web visit 
>>>>>>>>>>>>>> https://groups.google.com/d/msgid/pyqtgraph/c2fc8530-f073-407f-9539-dc82f8fbb875%40googlegroups.com
>>>>>>>>>>>>>>  
>>>>>>>>>>>>>> <https://groups.google.com/d/msgid/pyqtgraph/c2fc8530-f073-407f-9539-dc82f8fbb875%40googlegroups.com?utm_medium=email&utm_source=footer>
>>>>>>>>>>>>>> .
>>>>>>>>>>>>>> For more options, visit https://groups.google.com/d/optout.
>>>>>>>>>>>>>>
>>>>>>>>>>>>>
>>>>>>>>>>>>> -- 
>>>>>>>>>>>> You received this message because you are subscribed to the 
>>>>>>>>>>>> Google Groups "pyqtgraph" group.
>>>>>>>>>>>> To unsubscribe from this group and stop receiving emails from 
>>>>>>>>>>>> it, send an email to pyqtgraph+...@googlegroups.com.
>>>>>>>>>>>> To view this discussion on the web visit 
>>>>>>>>>>>> https://groups.google.com/d/msgid/pyqtgraph/ae710fb0-771f-464b-9c03-cf184e37382d%40googlegroups.com
>>>>>>>>>>>>  
>>>>>>>>>>>> <https://groups.google.com/d/msgid/pyqtgraph/ae710fb0-771f-464b-9c03-cf184e37382d%40googlegroups.com?utm_medium=email&utm_source=footer>
>>>>>>>>>>>> .
>>>>>>>>>>>>
>>>>>>>>>>>> For more options, visit https://groups.google.com/d/optout.
>>>>>>>>>>>>
>>>>>>>>>>>
>>>>>>>>>>> -- 
>>>>>>>> You received this message because you are subscribed to a topic in 
>>>>>>>> the Google Groups "pyqtgraph" group.
>>>>>>>> To unsubscribe from this topic, visit 
>>>>>>>> https://groups.google.com/d/topic/pyqtgraph/mZiiLO8hS70/unsubscribe
>>>>>>>> .
>>>>>>>> To unsubscribe from this group and all its topics, send an email to 
>>>>>>>> pyqtgraph+...@googlegroups.com.
>>>>>>>> To view this discussion on the web visit 
>>>>>>>> https://groups.google.com/d/msgid/pyqtgraph/53d1d9d3-6d9c-4b16-941a-358295c54995%40googlegroups.com
>>>>>>>>  
>>>>>>>> <https://groups.google.com/d/msgid/pyqtgraph/53d1d9d3-6d9c-4b16-941a-358295c54995%40googlegroups.com?utm_medium=email&utm_source=footer>
>>>>>>>> .
>>>>>>>>
>>>>>>>> For more options, visit https://groups.google.com/d/optout.
>>>>>>>>
>>>>>>>
>>>>>>> -- 
>>>>>> You received this message because you are subscribed to a topic in 
>>>>>> the Google Groups "pyqtgraph" group.
>>>>>> To unsubscribe from this topic, visit 
>>>>>> https://groups.google.com/d/topic/pyqtgraph/mZiiLO8hS70/unsubscribe.
>>>>>> To unsubscribe from this group and all its topics, send an email to 
>>>>>> pyqtgraph+...@googlegroups.com.
>>>>>> To view this discussion on the web visit 
>>>>>> https://groups.google.com/d/msgid/pyqtgraph/bfd11fe1-f617-47d6-bcca-d9848ad04bf6%40googlegroups.com
>>>>>>  
>>>>>> <https://groups.google.com/d/msgid/pyqtgraph/bfd11fe1-f617-47d6-bcca-d9848ad04bf6%40googlegroups.com?utm_medium=email&utm_source=footer>
>>>>>> .
>>>>>>
>>>>>> For more options, visit https://groups.google.com/d/optout.
>>>>>>
>>>>>
>>>>> -- 
>>>> You received this message because you are subscribed to a topic in the 
>>>> Google Groups "pyqtgraph" group.
>>>> To unsubscribe from this topic, visit 
>>>> https://groups.google.com/d/topic/pyqtgraph/mZiiLO8hS70/unsubscribe.
>>>> To unsubscribe from this group and all its topics, send an email to 
>>>> pyqtgraph+...@googlegroups.com.
>>>> To view this discussion on the web visit 
>>>> https://groups.google.com/d/msgid/pyqtgraph/ee0ce5da-a424-4b63-b02e-1444e8d56672%40googlegroups.com
>>>>  
>>>> <https://groups.google.com/d/msgid/pyqtgraph/ee0ce5da-a424-4b63-b02e-1444e8d56672%40googlegroups.com?utm_medium=email&utm_source=footer>
>>>> .
>>>>
>>>> For more options, visit https://groups.google.com/d/optout.
>>>>
>>>
>>>

-- 
You received this message because you are subscribed to the Google Groups 
"pyqtgraph" group.
To unsubscribe from this group and stop receiving emails from it, send an email 
to pyqtgraph+unsubscr...@googlegroups.com.
To view this discussion on the web visit 
https://groups.google.com/d/msgid/pyqtgraph/3b4b5708-b466-47c8-a20b-650fb434a30a%40googlegroups.com.
For more options, visit https://groups.google.com/d/optout.

Reply via email to