geosolver/workbench/cameraHandler.py
kwikrick 22e159a5ad Changes to GeometricSolver:
- Added RigidConstraint.
- Depricated some methods (get_result, get_constrainedness) and 
added some new methods (get_solution, get_cluster, get_status).

Removed old SelectionConstraint and renamed FunctionConstraint to SelectionConstraint

Depricated ClusterSolver2D
Small bugfixes in cluster ClusterSolver3D

Renamed solvergui directory to workbench

Renamed solvertest directory to test
2009-10-09 12:23:02 +00:00

199 lines
6.6 KiB
Python

from includes import *
from camera import *
from geosolver.matfunc import Vec
class CameraHandler(QtCore.QObject):
""" The camerahandler handles the rotation, translation, zooming, fitting and other actions of the camera. """
def __init__(self, glViewport, parent = None):
""" Initialization of the camerhandler.
Parameters:
glViewport: the viewport which is controlled by the camera
parent: parent of the camerahandler
"""
QtCore.QObject.__init__(self, parent)
self.resolvePoint = Vec([0.0, 0.0, 0.0])
self.lastMousePos = QtCore.QPoint(0,0)
self.lastMousePosOnSphere = Vec([0.0, 0.0, 0.0])
self.activeMouseAction = None
self.glViewport = glViewport
self.spinningQuaternion = Quaternion()
def mouseMoveEvent(self, mouseEvent, camera):
""" Handle the camera when there is a mousemove event. This can result in different actions, dependent on the chosen action by the user.
Parameters:
mouseEvent - mouse event, which contains the current position in the view
camera - the camera for which the action must be handled
"""
dx = mouseEvent.x() - self.lastMousePos.x()
dy = mouseEvent.y() - self.lastMousePos.y()
proj = self.projectToTrackball(camera, mouseEvent.x(), mouseEvent.y())
if self.activeMouseAction == None:
pass
elif self.activeMouseAction == MouseAction.TRANSLATE:
if mouseEvent.buttons() == self.glViewport.getMouseState(self.activeMouseAction):
self.handleMouseMove(camera, dx, dy)
elif self.activeMouseAction == MouseAction.ZOOM:
if mouseEvent.buttons() == self.glViewport.getMouseState(self.activeMouseAction):
self.handleMouseZoom(camera, dx, dy)
elif self.activeMouseAction == MouseAction.ROTATE:
if mouseEvent.buttons() == self.glViewport.getMouseState(self.activeMouseAction):
self.handleMouseRotate(camera, mouseEvent.x(), mouseEvent.y(), dx, dy, proj)
elif self.activeMouseAction == MouseAction.FIT:
if mouseEvent.buttons() == self.glViewport.getMouseState(self.activeMouseAction):
self.handleFit(camera)
self.lastMousePosOnSphere = proj
self.lastMousePos.setX(mouseEvent.pos().x())
self.lastMousePos.setY(mouseEvent.pos().y())
def handleMouseMove(self, camera, dx, dy):
""" Handle the translation of the camera based on the current and last mouse position.
Parameters:
camera - the camera that needs to be translated
dx - current x mouseposition in the view
dy - current y mouseposition in the view
"""
translation = Vec([dx, -dy, 0.0])
if camera.getCameraType() == CameraType.PERSPECTIVE:
#check = camera.coordinatesOf([0.0,0.0,0.0])
#print "check: " , check[2]
#choke = 2.0 * math.tan(check[2]) / camera.getScreenHeight()
#print "choke: " , choke
#translation *= choke
#print translation
translation[0] *= 2.0
translation[1] *= 2.0
#cameraPos[2] += dy*trans
else:
cameraPos = camera.getPosition()
translation[1] *= 2.0
translation[0] *= 2.0
self.translate(camera, translation)
def handleMouseZoom(self, camera, dx, dy):
""" Handle the zooming of the camera based on the current and last mouse position.
Parameters:
camera - the camera that needs to zoom
dx - difference between the last and current x mouse position
dy - difference between the last and current y mouse position
"""
self.translate(camera, Vec([0.0, 0.0, dy*2.0]))
def handleMouseRotate(self, camera, newMouseX, newMouseY, dx, dy, projection):
""" Handle the rotation of the camera based on the current and last mouse position.
Parameters:
camera - the camera that needs to be rotated
newMouseX - current x mouseposition in the view
newMouseY - current y mouseposition in the view
dx - difference between the last and current x mouse position
dy - difference between the last and current y mouse position
projection - projection of the mouseposition on a trackball
"""
#camera.orientation = camera.orientation * rotQuat
self.translate(camera, Vec([dx, dy, 0.0]))
camera.lookAt(self.resolvePoint)
#print "position: ",camera.getPosition()
#print "orientation: ",camera.getOrientation()
#print "revolvepoint: ",self.resolvePoint
def projectToTrackball(self, camera, newX, newY):
""" Project the mouseposition onto a trackball to rotate the camera.
Parameters:
newX - new x position on the trackball
newY - new y position on the trackball
Return:
vector - position on the trackball
"""
x = newX / (camera.getWindowWidth() / 2.0)
y = newY / (camera.getWindowHeight() / 2.0)
x = x -1
y = 1-y
z2 = 1 - (x * x + y * y)
z = 0.0
if z2 > 0 :
z = math.sqrt(z2)
#print " x, y, z on sphere: " , x, y, z
p = Vec([x,y,z])
p.normalize()
return p
def rotationFromMove(self, vFrom, vTo):
rotAxis = vTo.cross(vFrom)
d = Vec(vFrom - vTo)
t = d.norm()/(2.0*1.0)
phi = 2.0*math.asin(t)
rotQuat = Quaternion()
rotQuat.fromAxisAngle(rotAxis, phi)
rotQuat.normalize()
return rotQuat
def mouseWheelEvent(self, event, camera):
pass
def mouseReleaseEvent(self, event, camera):
pass
def handleFit(self, camera):
center = camera.getSceneCenter()
radius = camera.getSceneRadius()
distance = 0.0
cameraType = camera.getCameraType()
if cameraType == CameraType.PERSPECTIVE:
yView = radius / math.sin(camera.getFieldOfView()/2.0)
xView = radius / math.sin(camera.getHorizontalFov()/2.0)
if xView >= yView:
distance = xView
else:
distance = yView
elif cameraType == CameraType.ORTHOGRAPHIC:
distance = ((center - camera.getRevolveAroundPoint()) * camera.getViewDirection()) + (radius/camera.orthoCoef)
position = Vec(center-distance * camera.getViewDirection())
camera.setPosition(position)
"""slot"""
def setActiveMouseaction(self, action):
self.activeMouseAction = action
def translate(self, camera, translation):
pos = camera.getPosition()
trans = camera.getOrientation().rotate(translation)
pos[0] += trans[0]
pos[1] += trans[1]
pos[2] += trans[2]
def spin(self, camera):
self.rotateAroundPoint(camera, self.spinningQuaternion, camera.getRevolveAroundPoint())
def rotateAroundPoint(self, camera, spinQuat, point):
cameraOrientation = camera.getOrientation()
cameraOrientation *= spinQuat
cameraOrientation.normalize()
tempQuat = Quaternion()
tempQuat.fromAxisAngle(spinQuat.axis(), spinQuat.angle())
#print "pos: ", camera.getPosition(), " point: ", point
translation = point + tempQuat.rotate(camera.getPosition()-point) - camera.getPosition()
pos = camera.getPosition()
pos[0] += translation[0]
pos[1] += translation[1]
pos[2] += translation[2]
def getMainWindow(self):
""" Return the main window. """
return self.glViewport.getMainWindow()