Saturday, January 15, 2011

Camera control program

Well, what we have here is a class you can add to your programs to control your camera much like you would in a strategy game without a central actor. It's really good for experements and I hope you use it. In your main program you are going to want to add the line:
from cam import Cam as well as self.cam=Cam() to any program. You will want to remove the marker actor that shows where the center of the camera from your finished project or maybe put something like a colored lamp to make it look classy. In the meantime find some model to put in there, obviously it's not going to work out of the box for that reason.

from direct.showbase.DirectObject import DirectObject
import sys, time
from direct.gui.OnscreenText import OnscreenText
from pandac.PandaModules import *
from direct.actor.Actor import Actor
from math import sin, cos, radians

class Cam(DirectObject):

def __init__(self):
#camr Movement
self.vel = Vec3(0.0,0.0,0.0)
self.spin=Vec3(0, 0, 0)
self.forwardspeed = 19.0
self.backspeed = 17.0
self.risespeed=10.0
self.rotspeed=1
self.pitspeed=1
self.zoomrate=10
self.zoomlvl=10
#Hide mouse
props = WindowProperties()
props.setCursorHidden(False)
base.win.requestProperties(props)
base.disableMouse()


#create the camr
self.camr = NodePath(ActorNode("camr"))
self.camr.reparentTo(render)
base.camera.reparentTo(self.camr)
self.marker = Actor("/home/stephen/daes/marker.x" )
self.marker.reparentTo(self.camr)
self.camr.setPos(0,0,100)
base.camera.setPos(0, self.zoomlvl, 0)
base.camera.lookAt(self.camr)
self.marker.setColor(1, 0, 0)
self.camr.setP(self.camr, 35)
self.camr.setPos( 0, 0, 0 )
self.marker.setScale(0.2)
#Grab input and run task
self.accept("escape", sys.exit)
self.keyMap = {"forward":0,"backward":0,"strafeleft":0,"straferight":0,"riseup":0,"risedown":0, "lookdown":0, "lookup":0 }
self.accept("w",self.setKey, ["forward",1])
self.accept("s",self.setKey, ["backward",1])
self.accept("a",self.setKey, ["strafeleft",1])
self.accept("d",self.setKey, ["straferight",1])
self.accept("wheel_up", self.zoom, [1])
self.accept("wheel_down", self.zoom, [-1])
self.accept("z",self.setKey, ["riseup",1])
self.accept("x",self.setKey, ["risedown",1])
self.accept("w-up",self.setKey, ["forward",0])
self.accept("s-up",self.setKey, ["backward",0])
self.accept("a-up",self.setKey, ["strafeleft",0])
self.accept("d-up",self.setKey, ["straferight",0])
self.accept("z-up",self.setKey, ["riseup",0])
self.accept("x-up",self.setKey, ["risedown",0])
self.accept("q",self.setKey, ["lookdown", 1])
self.accept("q-up",self.setKey, ["lookdown", 0])
self.accept("e",self.setKey, ["lookup", 1])
self.accept("e-up",self.setKey, ["lookup", 0])


taskMgr.add(self.updatecamr, "updatecamr")
self.setupTxt()
def zoom(self, amt):
self.zoomlvl+=amt*self.zoomrate
base.camera.setPos(0, self.zoomlvl, 0)
def updateTxt(self):
self.poso.destroy()
self.oro.destroy()
self.setupTxt()
def setupTxt(self):
self.poso=OnscreenText(`self.camr.getPos()`, pos = (-1.3, .95-.05*0), fg=(1,1,1,1), align = TextNode.ALeft, scale = .05, mayChange = 0)
self.oro= OnscreenText(`self.camr.getHpr()`, pos = (-1.3, .95-.05*1), fg=(1,1,1,1), align = TextNode.ALeft, scale = .05, mayChange = 0)


def setKey(self, key, value):
self.keyMap[key] = value

def updatecamr(self, task):
"""Big task that updates the camrs position every tick"""
elapsed = globalClock.getDt()
# reset mouse coords for next iteration
x = 0.0
y = 0.0
z = 0.0
rot=0.0
pit=0.0
#Move the camr around
if (self.keyMap["strafeleft"]!=0):
rot = -self.rotspeed
self.camr.setH(self.camr.getH()%360)
if (self.keyMap["straferight"]!=0):
rot = self.rotspeed
self.camr.setH(self.camr.getH()%360)
if (self.keyMap["forward"]!=0):
x = self.forwardspeed *sin(radians(self.camr.getH()))
y = - self.forwardspeed *cos(radians(self.camr.getH()))
if (self.keyMap["backward"]!=0):
x = -self.forwardspeed *sin(radians(self.camr.getH()))
y = self.forwardspeed *cos(radians(self.camr.getH()))
if(self.keyMap["riseup"]!=0):
z= self.risespeed
if(self.keyMap["risedown"]!=0):
z= -self.risespeed
if(not(self.camr.getP()>=70) and (self.keyMap["lookup"]!=0)):
pit+= self.pitspeed
if(not(self.camr.getP()<=10) and (self.keyMap["lookdown"]!=0)):
pit-= self.pitspeed
# (x, y)=(sin(radians(self.camr.getH())), cos(radians(self.camr.getH())))
self.vel = Vec3(x,y,z)
self.vel *= elapsed
self.spin=Vec3(rot, pit, 0.0)
#self.spin *= elapsed
self.camr.setFluidPos(self.camr.getPos()+ self.vel)
self.camr.setHpr(self.camr.getHpr()+ self.spin)
#self.camr.setP(pit)
self.updateTxt()
return task.cont


No comments:

Post a Comment