예제 #1
0
 def pick(self, x, y, viewer):
     if viewer.getSceneData():
         if self.usePolytopeIntersector():
             picker = osgUtil.PolytopeIntersector(osgUtil.Intersector.WINDOW, x - 2.0, y - 2.0, x + 2.0, y + 2.0)
         else:
             picker = osgUtil.LineSegmentIntersector(osgUtil.Intersector.WINDOW, x, y)
         intersectionVisitor = osgUtil.IntersectionVisitor(picker)
         viewer.getCamera().accept(intersectionVisitor)
         if picker.containsIntersections():
             intersections = picker.getIntersections()
             
             # The PolytopeIntersector mis-calculates the eye distance for geometry nested under a transform, which is true for all UnitShapes.  (See the thread at http://www.mail-archive.com/[email protected]/msg29195.html for some discussion.)
             # Calculate the correct distance and re-sort.
             # This will probably still work correctly after that bug is fixed but will be inefficient.
             visibleHits = []
             eye, center, up = (osg.Vec3(), osg.Vec3(), osg.Vec3())
             viewer.getCamera().getViewMatrixAsLookAt(eye, center, up)
             eye = (eye.x(), eye.y(), eye.z())
             for i in range(0, len(intersections)):
                 intersection = intersections[i]
                 for j in range(0, len(intersection.nodePath)):
                     node = intersection.nodePath[j]
                     geode = osg.NodeToGeode(node)
                     if geode != None:
                         visibleID = int(geode.getName())
                         visible = self._display.visibleWithId(visibleID)
                         if geode.getOrCreateStateSet().getAttribute(osg.StateAttribute.DEPTH):
                             # If a geode has this attribute set then (currently) it is being rendered in front of all other nodes.  Simulate this here by placing the geode right at the eye.
                             # If depths other than the default or osg.Depth.ALWAYS are used in the future then this check will need to be modified.
                             eyeDistance = 0.0
                         else:
                             intersectionPoint = intersection.localIntersectionPoint
                             if isinstance(visible.shape(), UnitShape):
                                 position = visible.worldPosition()
                                 size = visible.worldSize()
                                 intersectionPoint = (position[0] + size[0] * intersectionPoint.x(), position[1] + size[1] * intersectionPoint.y(), position[2] + size[2] * intersectionPoint.z())
                             eyeDistance = (intersectionPoint[0] - eye[0]) ** 2 + (intersectionPoint[1] - eye[1]) ** 2 + (intersectionPoint[2] - eye[2]) ** 2
                         visibleHits += [(eyeDistance, visible)]
             visibleHits.sort()
             
             # Loop through all of the hits to find the "deepest" one in the sense of the visible hierarchy.  For example, a neuron in a region will be picked instead of the region even though the region hit is closer.
             if self._display.useGhosts():
                 # Make a first pass only picking non-ghosted items.
                 # TODO: this could be done with node masks...
                 deepestVisible = None
                 for distance_, visible in visibleHits:
                     if (visible in self._display.highlightedVisibles or visible in self._display.animatedVisibles) and (deepestVisible is None or deepestVisible in visible.ancestors()):
                         deepestVisible = visible
                 if deepestVisible is not None:
                     self._display.selectVisibles([deepestVisible], self._display.selectionShouldExtend, self._display.findShortestPath, fromclick=True)
                     return True
             deepestVisible = None
             for distance_, visible in visibleHits:
                 if deepestVisible is None or deepestVisible in visible.ancestors():
                     deepestVisible = visible
             self._display.selectVisibles([deepestVisible], self._display.selectionShouldExtend, self._display.findShortestPath, fromclick=True)
         else:
             self._display.selectVisibles([])
     return True
예제 #2
0
 def startDragPanOrPick(self, eventAdaptor, viewer):
     eventWasHandled = False
     if viewer.getSceneData():
         # TODO: This is a major hack.  The intersection code below always picks the composite dragger, even if it isn't being rendered.  So we remove the inactive dragger while picking.
         # TODO: Figure out how to make the intersection code honor the LOD and get rid of the DraggerCullCallback class.
         if self._display.draggerLOD is not None:
             if self._display.activeDragger == self._display.simpleDragger:
                 self._display.draggerLOD.removeChild(
                     self._display.compositeDragger)
             if self._display.activeDragger == self._display.compositeDragger:
                 self._display.draggerLOD.removeChild(
                     self._display.simpleDragger)
         x, y = eventAdaptor.getX(), eventAdaptor.getY()
         if self.usePolytopeIntersector():
             picker = osgUtil.PolytopeIntersector(
                 osgUtil.Intersector.WINDOW, x - 2.0, y - 2.0, x + 2.0,
                 y + 2.0)
         else:
             picker = osgUtil.LineSegmentIntersector(
                 osgUtil.Intersector.WINDOW, x, y)
         intersectionVisitor = osgUtil.IntersectionVisitor(picker)
         intersectionVisitor.setTraversalMode(
             osg.NodeVisitor.TRAVERSE_ACTIVE_CHILDREN)
         viewer.getCamera().accept(intersectionVisitor)
         if picker.containsIntersections():
             # Add all intersections from the first dragger hit onward to the pointer info.  This allows dragging of nested regions.
             self.pointerInfo.setCamera(viewer.getCamera())
             self.pointerInfo.setMousePosition(eventAdaptor.getX(),
                                               eventAdaptor.getY())
             intersections = picker.getIntersections()
             for i in range(0, len(intersections)):
                 intersection = intersections[i]
                 for j in range(0, len(intersection.nodePath)):
                     node = intersection.nodePath[j]
                     if self.dragger is None:
                         self.dragger = osgManipulator.NodeToDragger(node)
                     if self.dragger is not None:
                         localPoint = intersection.localIntersectionPoint  # have to do stupid conversion from Vec3d to Vec3
                         if self.usePolytopeIntersector():
                             self.pointerInfo.addIntersection(
                                 intersection.nodePath,
                                 osg.Vec3(localPoint.x(), localPoint.y(),
                                          localPoint.z()))
                         else:
                             self.pointerInfo.addIntersection(
                                 intersection.nodePath,
                                 osg.Vec3d(localPoint.x(), localPoint.y(),
                                           localPoint.z()))
             if self.dragger is not None:
                 self.dragger.handle(self.pointerInfo, eventAdaptor, viewer)
                 eventWasHandled = True
         if self._display.draggerLOD is not None:
             if self._display.activeDragger == self._display.simpleDragger:
                 self._display.draggerLOD.addChild(
                     self._display.compositeDragger)
             if self._display.activeDragger == self._display.compositeDragger:
                 self._display.draggerLOD.addChild(
                     self._display.simpleDragger)
     return eventWasHandled
예제 #3
0
 def pick(self, x, y, viewer):
     print "Picking"
     if not viewer.getSceneData():
         return False
     #create an intersector
     picker = osgUtil.LineSegmentIntersector(osgUtil.Intersector.PROJECTION,
                                             x, y)
     #create an intersectionVisitor
     iv = osgUtil.IntersectionVisitor(picker)
     #visit the sceneGraph
     viewer.getCamera().accept(iv)
     #check for intersections
     if picker.containsIntersections():
         print "Intersection Found"
         intersection = picker.getFirstIntersection()
         #find the first Transform node and make it the selected node
         for node in intersection.nodePath:
             mt = osg.NodeToMatrixTransform(node)
             if mt:
                 #if there is a previous selected node, 'deselect' it
                 if self._selectedNode:
                     self._selectedNode.setUpdateCallback(
                         osg.NodeCallback())
                     #remove the wirebox of the previous selection
                     if self.wb:
                         self._selectedNode.removeChild(self.wb)
                 self._selectedNode = mt
                 #show that the node is selected
                 mt.setUpdateCallback(RotateCB().__disown__())
             else:
                 pot = osg.NodeToPositionAttitudeTransform(node)
                 if pot:
                     #if there is a previous selected node, 'deselect' it
                     if self._selectedNode:
                         self._selectedNode.setUpdateCallback(None)
                         #remove the wirebox of the previous selection
                         if self.wb:
                             self._selectedNode.removeChild(self.wb)
                     self._selectedNode = pot
                     #show that the node is selected
                     pot.setUpdateCallback(RotateCB().__disown__())
                 else:
                     geode = osg.NodeToGeode(node)
                     if geode:
                         #create a wirebox and safe it, the wire box
                         #will be attached to the parental transform node
                         self.wb = createWireBox(geode)
                         self._selectedNode.addChild(self.wb)
                         self.wb.thisown = False
                         return True
         return False
     else:
         print "No Intersection Found"
     return False