예제 #1
0
    def set_controls(self):
        """Configure common game controls.

        Configure major keys, collisions system
        and controls to manipulate characters.
        """
        base.accept("f1", self._show_keys)  # noqa: F821
        base.accept("escape", base.main_menu.show)  # noqa: F821
        base.accept("r", self._show_char_relations)  # noqa: F821
        base.accept("m", base.world.rails_scheme.show)  # noqa: F821
        base.accept("j", base.journal.show)  # noqa: F821

        # configure mouse collisions
        col_node = CollisionNode("mouse_ray")
        col_node.setIntoCollideMask(NO_MASK)
        col_node.setFromCollideMask(MOUSE_MASK)
        self._mouse_ray = CollisionRay()
        col_node.addSolid(self._mouse_ray)

        # set common collisions handler
        handler = CollisionHandlerEvent()
        handler.addInPattern("%fn-into")
        handler.addAgainPattern("%fn-again")
        handler.addOutPattern("%fn-out")

        self.traverser = CollisionTraverser("traverser")
        self.traverser.addCollider(
            base.cam.attachNewNode(col_node), handler  # noqa: F821
        )
        self.set_mouse_events()

        taskMgr.doMethodLater(0.03, self._collide_mouse, "collide_mouse")  # noqa: F821
        taskMgr.doMethodLater(0.04, self._traverse, name="main_traverse")  # noqa: F821
예제 #2
0
class CollisionBase(ShowBase):
    def __init__(self):
        self.cTrav = CollisionTraverser()
        self.mchandler = CollisionHandlerEvent()
        self.mchandler.addInPattern('into-%in')
        self.mchandler.addAgainPattern('%fn-again-%in')
        self.mchandler.addOutPattern('out-%in')
예제 #3
0
 def __init__(self, model = "cube_nocol", texture = "lava", pos = (0,0,0), scale = (1,1,1), cubetype = "A"):
     super(LavaCube, self).__init__(model, texture, pos, scale)
     cn = CollisionNode('lava')
     cn.setFromCollideMask(COLLISIONMASKS['lava'])
     cn.setIntoCollideMask(BitMask32.allOff())
     np = self.node.attachNewNode(cn)
     cn.addSolid(CollisionSphere(0,0,0,1.1))
     h = CollisionHandlerEvent()
     h.addInPattern('%fn-into-%in')
     h.addOutPattern('%fn-outof-%in')
     base.cTrav.addCollider(np, h)
예제 #4
0
 def __init__(self, model = "models/sphere", texture = "exit", pos = (0,0,0), scale = (1,1,1), cubetype = "A"):
     super(LevelExit, self).__init__(model, texture, pos, scale)
     #self.node.setTransparency(TransparencyAttrib.MAlpha)
     self.node.setTag('noportals', '1')
     self.node.setTag('isexit', '1')
     cn = CollisionNode('levelExit')
     cn.setFromCollideMask(COLLISIONMASKS['exit'])
     cn.setIntoCollideMask(BitMask32.allOff())
     np = self.node.attachNewNode(cn)
     cn.addSolid(CollisionSphere(0,0,0,1.1))
     h = CollisionHandlerEvent()
     h.addInPattern('%fn-into-%in')
     h.addOutPattern('%fn-outof-%in')
     base.cTrav.addCollider(np, h)
예제 #5
0
 def createPortalCollisions(self):
     # Enter the portals
     cn = CollisionNode('bluePortal')
     cn.setFromCollideMask(COLLISIONMASKS['portals'])
     cn.setIntoCollideMask(BitMask32.allOff())
     np = self.bluePortal.attachNewNode(cn)
     cn.addSolid(CollisionSphere(0,0,0,2))
     h = CollisionHandlerEvent()
     h.addInPattern('%fn-into-%in')
     h.addOutPattern('%fn-outof-%in')
     self.base.cTrav.addCollider(np, h)
     cn = CollisionNode('orangePortal')
     cn.setFromCollideMask(COLLISIONMASKS['portals'])
     cn.setIntoCollideMask(BitMask32.allOff())
     np = self.orangePortal.attachNewNode(cn)
     cn.addSolid(CollisionSphere(0,0,0,2))
     h = CollisionHandlerEvent()
     h.addInPattern('%fn-into-%in')
     h.addOutPattern('%fn-outof-%in')
     self.base.cTrav.addCollider(np, h)
예제 #6
0
class Pickup(DirectObject):

    #Creates health pickup object
    def __init__(self, idappend, spawn):
        
        self.id = "pick"+str(idappend)
        self.deletePickup = False          
        self.projectileNode = NodePath('heal'+str(self.id))

        self.projectileNode.setScale(1)
        self.projectileModel = loader.loadModel("./resources/healthPickup.egg")
        self.projectileModel.setColorScale(200, 0, 0, 100)
        self.projectileModel.reparentTo(self.projectileNode)
        self.projectileNode.reparentTo(render)
        self.projectileNode.setPos(spawn)
        cs = CollisionSphere(0, 0, 0, .5)
        cnode = CollisionNode('heal')
        self.colNode = self.projectileModel.attachNewNode(cnode)
        self.colNode.node().addSolid(cs)
        self.collHand = CollisionHandlerEvent()
        self.collHand.addInPattern('pickupin'+str(self.id))
        self.collHand.addOutPattern('oot')
        base.cTrav.addCollider(self.colNode, self.collHand)
        self.accept('pickupin'+str(self.id), self.pickup)
   
    #Detects if the player has picked up the health
    def pickup(self, col):
        
        if col.getIntoNodePath().getName() == "cnode":

            messenger.send("pickuphealth")
            self.deletePickup = True

    #Destroys the health pickups from the scene graph
    def destroy(self):

        self.projectileNode.removeNode()
        self.projectileModel.removeNode()
        self.colNode.node().clearSolids()
        
        del self
예제 #7
0
class DKApp(ShowBase):
    def __init__(self):
        super().__init__(self)

        self.scene = self.loader.loadModel("models/DKSet1")
        self.scene.reparentTo(self.render)
        self.scene.setPos(0,0,0)
        self.jumping  = False
        self.jumpTime = 0
        # base.messenger.toggleVerbose()
        self.accept("raw-arrow_left" , self.pressLeft)
        self.accept("raw-arrow_left-up", self.releaseLeft)
        self.accept("raw-arrow_right" , self.pressRight)
        self.accept("raw-arrow_right-up", self.releaseRight)

        self.accept("raw-space" , self.pressSpace)
        self.accept("raw-space-up", self.releaseSpace)
        self.accept("raw-arrow_up" , self.pressUp)
        self.accept("raw-arrow_up-up", self.releaseUp)

        self.taskMgr.add(self.setup,"setup")
        self.taskMgr.add(self.update , "update")


        self.input=  {
            "up":False,
            "left":False,
            "right":False,
            "space":False
        }

    def pressLeft(self):
        self.input["left"] = True
    def releaseLeft(self):
        self.input["left"] = False
    def pressRight(self):
        self.input["right"] = True
    def releaseRight(self):
        self.input["right"] = False

    def pressSpace(self):
        self.input["space"] = True
    def releaseSpace(self):
        self.input["space"] = False
    def pressUp(self):
        self.input["up"] = True
    def releaseUp(self):
        self.input["up"] = False

    def getHorizontalAxis(self):
        if( self.input["left"] and self.input["right"]):
            return 0
        if( self.input["left"] ):
            return -1
        if( self.input["right"]):
            return 1

        return 0
    def setupCollision(self):
        base.cTrav = CollisionTraverser()
        self.collisionHandlerEvent = CollisionHandlerEvent()
        self.collisionHandlerEvent.addInPattern('into-%in')
        self.collisionHandlerEvent.addOutPattern('outof-%in')

        hitBox = CollisionBox(  Point3(7,0,-4.5) , 0.5,5,0.5)
        cnodePath = self.player.attachNewNode( CollisionNode('marioHitBox') )
        cnodePath.node().addSolid(hitBox)
        cnodePath.show()
        base.cTrav.addCollider(cnodePath, self.collisionHandlerEvent)

        stairs1 =  self.scene.find("root/bottomstair")
        hitBox = CollisionBox(  Point3(-6.8,0,-3.0) , 0.5,5,2.5)
        cnodePath = stairs1.attachNewNode( CollisionNode('stairsHitBox') )
        cnodePath.node().addSolid(hitBox)


        cnodePath.show()

        self.accept('into-stairsHitBox', self.enableStair)
        self.accept('outof-stairsHitBox', self.disableStair)
        base.cTrav.showCollisions(self.render)

    def enableStair(self, evt):
        print(f'{evt}')

    def disableStair(self, evt):
        print(f'{evt}')

    def setup(self, task):
        lens = OrthographicLens()
        lens.setFilmSize(25,20)
        base.camNode.setLens(lens)

        node = self.scene.find("root/camera1")
        node.remove()

        self.player = self.scene.find("root/mario")
        self.setupCollision()
        return Task.done

    def update(self,task):
        self.camera.setPos(0,35,0)
        self.camera.lookAt(self.scene)
        # print(f'{globalClock.getDt()}')

        jy = 0  # jump Y/Z
        vi = 4 # initial velocity
        g = -5 # gravity
        if self.jumping:
            self.jumpTime = self.jumpTime + globalClock.getDt()
            jy = vi*self.jumpTime  + 0.5*g*self.jumpTime*self.jumpTime
            vy = vi + g*self.jumpTime
            if vy < 0 and abs(jy) < 0.2: # eventually jy substraction will change for the original y(aka Z) mario had
                self.jumpTime = 0
                self.jumping = False
                jy = 0
        else:
            if self.player.getZ() == 0 and  self.input["space"] :
                self.jumping = True
                self.jumpTime = 0.01

        # stop advancing if jumping!
        adv = self.getHorizontalAxis()*-.2
        if self.jumping :
            adv = 0
        self.player.setPos( self.player.getX()+adv , 0, jy   )
        return Task.cont
예제 #8
0
    # this is what set our ray to shoot from the actual camera lenses off the 3d scene, passing by the mouse pointer position, making  magically hit in the 3d space what is pointed by it
    pickerRay.setFromLens(base.camNode, mpos.getX(),mpos.getY())
  return task.cont

#** This function then will be called when we click and release the left mouse button, showing himself changing the ball scale according with the pickingEnabled flag state.
def mousePick(status):
  if pickingEnabled:
    if status == 'down':
      smileyModel.setScale(.9)

  if status == 'up':
    smileyModel.setScale(1.0)

# Here as well we see something already seen in the previous steps related to collision events so I won't go into details.
collisionHandler.addInPattern('%fn-into-%in')
collisionHandler.addOutPattern('%fn-out-%in')

#** Let's manage now the collision events:
DO=DirectObject()
# if you went from step3 and step4, here should not be mysteries for you
DO.accept('mouseraycnode-into-smileycnode', collideEventIn)
DO.accept('mouseraycnode-out-smileycnode', collideEventOut)

#** This little but important variable will be used to know the picking state at any time - note that the picking is enabled ASA the mouse pointer goes above the ball and disabled when it leave.
pickingEnabled=False

#** This is how we interact with mouse clicks - see the mousePick function above for details
DO.accept('mouse1', mousePick, ['down'])
DO.accept('mouse1-up', mousePick, ['up'])

#** And at last, we start the task that continuously update the ray collider position and orientation while we move the mouse pointer
예제 #9
0
class CBShield(DirectObject):
    
    #Property stuff
    creaTime = time.clock()
    dur = 5
    vec = 0
    delta = .15
    prevtime = 0
    flag = False
    
    #defining the thing fired by whatever gun we have
    def __init__(self, camera, look, id):
        
        #nodepath of the projectile, give it a trajectory
        self.projectileNode = NodePath('projectile'+str(id))
        self.projectileNode.setTransparency(TransparencyAttrib.MAlpha)
        self.projectileNode.reparentTo(render)
        
        #by passing the camera node form the camMov object, all projectiles are spawned 5 units in front of the camera
        self.projectileNode.setHpr(look, 0, 0, 0)
        self.projectileNode.setPos(camera,-1,10, 3)
        
        #fix z position to line up with gun
        self.projectileNode.setScale(.1)
        projectileModel = loader.loadModel("./resources/cubeShot.egg")
        projectileModel.setColorScale(0, 0, 0, .5)
        projectileModel.setSz(50)
        projectileModel.setSy(1)
        projectileModel.setSx(50)
        projectileModel.reparentTo(self.projectileNode)
    	
        #must calculate unit vector based on direction
        dir = render.getRelativeVector(look, Vec3(0, 1, 0))
    	
        #speed up or slow down projectiles here
        dir = dir*10
        self.vec = dir
        
        #base.cTrav = CollisionTraverser()
        cs = CollisionSphere(0, 0, 0, 25)
        cnodepath = self.projectileNode.attachNewNode(CollisionNode('projNode'))
        cnodepath.node().addSolid(cs)
        self.collHand = CollisionHandlerEvent()
        self.collHand.addInPattern('into'+str(id))
        self.collHand.addOutPattern('outof')
        
        #cTrav has the distinction of global colider handler
        base.cTrav.addCollider(cnodepath, self.collHand)
        self.acceptOnce('into'+str(id), self.hit)
      
	    #deal with colliding or special effects here.
	    #wanted projectiles to be short lived
	    #so i will make them delete themselves after impact or time expired
        #writing a task that will rek the projectiles at the end of time
        self.damage = 20
    
    def placeTask(self, task):
        
        #curtime = time.clock()
        #self.delta = curtime-self.prevtime
        
        if self.flag:
            return task.done
        
        #prevtime = time.clock()
            
        
        if task.time < self.dur:
        
            return task.cont
        else:
            
            self.flag = True
            return task.done
        

    def hit(self, collEntry):
        #throw out a custom message for what hit
        if collEntry.getIntoNodePath().getName() != 'projNode':
           
            temp = collEntry.getIntoNodePath().getName()
            messenger.send(temp, [self.damage]) 
            
            #remove the impacting projectile
            collEntry.getFromNodePath().getParent().getParent().removeNode()
            self.flag =  True
            del self
예제 #10
0
class GameContainer(ShowBase):

    def __init__(self):

        ShowBase.__init__(self)

        ########## Window configuration #########

        wp = WindowProperties()
        wp.setSize(1024, 860)

        self.win.requestProperties(wp)

        ########## Gameplay settings #########

        self.GAME_MODE = PLAY
        self.play_mode = SPACE

        self.level = 1.5

        self.mode_initialized = False

        ######### Camera #########

        self.disableMouse()

        self.mainCamera = Camera(self.camera)

        self.mainCamera.camObject.setHpr(0, 0, 0)

        #Trigger game chain

        self.loadLevel(LEVEL)

        ######### Events #########

        self.taskMgr.add(self.gameLoop, "gameLoop", priority = 35)

        self.keys = {"w" : 0, "s" : 0, "a" : 0, "d" : 0, "space" : 0}

        self.accept("w", self.setKey, ["w", 1])
        self.accept("w-up", self.setKey, ["w", 0])
        self.accept("s", self.setKey, ["s", 1])
        self.accept("s-up", self.setKey, ["s", 0])
        self.accept("a", self.setKey, ["a", 1])
        self.accept("a-up", self.setKey, ["a", 0])
        self.accept("d", self.setKey, ["d", 1])
        self.accept("d-up", self.setKey, ["d", 0])
        self.accept("space", self.setKey, ["space", 1])
        self.accept("space-up", self.setKey, ["space", 0])
        self.accept("wheel_up", self.zoomCamera, [-1])
        self.accept("wheel_down", self.zoomCamera, [1])
        self.accept("escape", self.switchGameMode, [IN_GAME_MENU])

        self.accept("window-event", self.handleWindowEvent)

        self.accept("playerGroundRayJumping-in", self.avatar.handleCollisionEvent, ["in"])
        self.accept("playerGroundRayJumping-out", self.avatar.handleCollisionEvent, ["out"])

        ######### GUI #########

        self.gui_elements = []

    def loadSpaceTexture(self, level):

        if level < 10: return 'textures/space#.jpg'
        elif level < 15: pass  

    def loadLevel(self, level):

        #Resets

        self.avatarActor = Actor("models/panda",
                                {"walk": "models/panda-walk"})
        self.avatarActor.setScale(.5, .5, .5)
        self.avatarActor.setHpr(180, 0, 0)
        self.avatarActor.setCollideMask(BitMask32.allOff())

        self.asteroidManager = AsteroidManager()

        #Alternate modes

        if int(self.level) == self.level: self.play_mode = TERRAIN

        else: self.play_mode = SPACE

        #Specifics

        if self.play_mode == SPACE:

            self.avatar = Avatar(self.avatarActor)
            self.avatar.objectNP.reparentTo(render)

            ########## Sky #########

            cubeMap = loader.loadCubeMap(self.loadSpaceTexture(self.level))
            self.spaceSkyBox = loader.loadModel('models/box')

            self.spaceSkyBox.setScale(100)
            self.spaceSkyBox.setBin('background', 0)
            self.spaceSkyBox.setDepthWrite(0)
            self.spaceSkyBox.setTwoSided(True)
            self.spaceSkyBox.setTexGen(TextureStage.getDefault(), TexGenAttrib.MWorldCubeMap)
            self.spaceSkyBox.setTexture(cubeMap, 1)
            #self.spaceSkyBox.setEffect(CompassEffect.make(render))

            parentNP = render.attachNewNode('parent')

            self.spaceSkyBox.reparentTo(parentNP)
            self.spaceSkyBox.setPos(-self.spaceSkyBox.getSx()/2, -self.spaceSkyBox.getSy()/2, 
                                    -self.spaceSkyBox.getSz()/2)

            self.asteroidManager.initialize(self.level)

        elif self.play_mode == TERRAIN:

            ########## Terrain #########

            #self.environ = loader.loadModel("../mystuff/test.egg")
            self.environ = loader.loadModel("models/environment")
            self.environ.setName("terrain")
            self.environ.reparentTo(render)
            self.environ.setPos(0, 0, 0)
            self.environ.setCollideMask(BitMask32.bit(0))

            ######### Models #########

            ######### Physics #########

            base.enableParticles()

            gravityForce = LinearVectorForce(0, 0, -9.81)
            gravityForce.setMassDependent(False)
            gravityFN = ForceNode("world-forces")
            gravityFN.addForce(gravityForce)
            render.attachNewNode(gravityFN)
            base.physicsMgr.addLinearForce(gravityForce)

            self.avatarPhysicsActorNP = render.attachNewNode(ActorNode("player"))
            self.avatarPhysicsActorNP.node().getPhysicsObject().setMass(50.)
            self.avatarActor.reparentTo(self.avatarPhysicsActorNP)
            base.physicsMgr.attachPhysicalNode(self.avatarPhysicsActorNP.node())

            self.avatarPhysicsActorNP.setPos(15, 10, 5)

            ######### Game objects #########

            self.avatar = Avatar(self.avatarPhysicsActorNP)

            ######### Collisions #########

            self.cTrav = CollisionTraverser()

            #Make player rigid body

            self.pandaBodySphere = CollisionSphere(0, 0, 4, 3)

            self.pandaBodySphereNode = CollisionNode("playerBodyRay")
            self.pandaBodySphereNode.addSolid(self.pandaBodySphere)
            self.pandaBodySphereNode.setFromCollideMask(BitMask32.bit(0))
            self.pandaBodySphereNode.setIntoCollideMask(BitMask32.allOff())

            self.pandaBodySphereNodepath = self.avatar.objectNP.attachNewNode(self.pandaBodySphereNode)
            self.pandaBodySphereNodepath.show()

            self.pandaBodyCollisionHandler = PhysicsCollisionHandler()
            self.pandaBodyCollisionHandler.addCollider(self.pandaBodySphereNodepath, self.avatar.objectNP)

            #Keep player on ground

            self.pandaGroundSphere = CollisionSphere(0, 0, 1, 1)

            self.pandaGroundSphereNode = CollisionNode("playerGroundRay")
            self.pandaGroundSphereNode.addSolid(self.pandaGroundSphere)
            self.pandaGroundSphereNode.setFromCollideMask(BitMask32.bit(0))
            self.pandaGroundSphereNode.setIntoCollideMask(BitMask32.allOff())

            self.pandaGroundSphereNodepath = self.avatar.objectNP.attachNewNode(self.pandaGroundSphereNode)
            self.pandaGroundSphereNodepath.show()

            self.pandaGroundCollisionHandler = PhysicsCollisionHandler()
            self.pandaGroundCollisionHandler.addCollider(self.pandaGroundSphereNodepath, self.avatar.objectNP)

            #Notify when player lands

            self.pandaGroundRayJumping = CollisionSphere(0, 0, 1, 1)

            self.pandaGroundRayNodeJumping = CollisionNode("playerGroundRayJumping")
            self.pandaGroundRayNodeJumping.addSolid(self.pandaGroundRayJumping)
            self.pandaGroundRayNodeJumping.setFromCollideMask(BitMask32.bit(0))
            self.pandaGroundRayNodeJumping.setIntoCollideMask(BitMask32.allOff())

            self.pandaGroundRayNodepathJumping = self.avatar.objectNP.attachNewNode(self.pandaGroundRayNodeJumping)
            self.pandaGroundRayNodepathJumping.show()

            self.collisionNotifier = CollisionHandlerEvent()
            self.collisionNotifier.addInPattern("%fn-in")
            self.collisionNotifier.addOutPattern("%fn-out")

            self.cTrav.addCollider(self.pandaGroundSphereNodepath, self.pandaGroundCollisionHandler)
            self.cTrav.addCollider(self.pandaGroundRayNodepathJumping, self.collisionNotifier)
            self.cTrav.addCollider(self.pandaBodySphereNodepath, self.pandaBodyCollisionHandler)

    def maintainTurrets(self):

        pass

    def setKey(self, key, value):

        self.keys[key] = value

    def zoomCamera(self, direction):

        Camera.AVATAR_DIST += direction

    def b(self, hey):

        self.avatarLanded = True

    def handleWindowEvent(self, window=None):

        wp = window.getProperties()

        self.win_center_x = wp.getXSize() / 2
        self.win_center_y = wp.getYSize() / 2

    def switchGameMode(self, newGameMode=None):

        self.cleanupGUI()

        if self.GAME_MODE == IN_GAME_MENU: 

            if newGameMode == PLAY:

                render.clearFog()

            elif newGameMode == MAIN_MENU:

                pass

        elif True:

            pass

        self.GAME_MODE = newGameMode

        self.mode_initialized = False

    def cleanupGUI(self):

        for gui_element in self.gui_elements:

            gui_element.destroy()

    def evenButtonPositions(self, button_spacing, button_height, num_buttons):

        center_offset = (button_spacing/(2.0) if (num_buttons % 2 == 0) else 0)

        button_positions = []

        current_pos = center_offset + ((num_buttons - 1)/2) * button_spacing

        for i in range(0, num_buttons):

            button_positions.append(current_pos + (button_height/2.0))

            current_pos -= button_spacing

        return button_positions

    def buildInGameMenu(self):

        props = WindowProperties()
        props.setCursorHidden(False) 
        base.win.requestProperties(props)

        resume_button = DirectButton(text = "Resume", scale = .1, command = (lambda: self.switchGameMode(PLAY)),
                                    rolloverSound=None)

        main_menu_button = DirectButton(text = "Main Menu", scale = .1, command = self.b,
                                    rolloverSound=None)

        options_button = DirectButton(text = "Options", scale = .1, command = self.b,
                                    rolloverSound=None)

        exit_button = DirectButton(text = "Exit", scale = .1, command = exit,
                                    rolloverSound=None)

        BUTTON_SPACING = .2
        BUTTON_HEIGHT = resume_button.getSy()

        button_positions = self.evenButtonPositions(BUTTON_SPACING, BUTTON_HEIGHT, 4)

        resume_button.setPos(Vec3(0, 0, button_positions[0]))
        main_menu_button.setPos(Vec3(0, 0, button_positions[1]))
        options_button.setPos(Vec3(0, 0, button_positions[2]))
        exit_button.setPos(Vec3(0, 0, button_positions[3]))

        self.gui_elements.append(resume_button)
        self.gui_elements.append(main_menu_button)
        self.gui_elements.append(options_button)
        self.gui_elements.append(exit_button)

    def buildMainMenu(self):

        props = WindowProperties()
        props.setCursorHidden(False) 
        base.win.requestProperties(props)

        start_game_button = DirectButton(text = "Start", scale = .1,
                            command = self.b)

        select_level_button = DirectButton(text = "Select Level", scale = .1,
                            command = self.b)

        game_options_button = DirectButton(text = "Options", scale = .1,
                            command = self.b)

        exit_button = DirectButton(text = "Exit", scale = .1,
                            command = exit)

        BUTTON_SPACING = .2
        BUTTON_HEIGHT = start_game_button.getSy()

        button_positions = self.evenButtonPositions(BUTTON_SPACING, BUTTON_HEIGHT)

        start_game_button.setPos(Vec3(0, 0, button_positions[0]))
        select_level_button.setPos(Vec3(0, 0, button_positions[1]))
        game_options_button.setPos(Vec3(0, 0, button_positions[2]))
        exit_button.setPos(Vec3(0, 0, button_positions[3]))

        self.gui_elements.append(start_game_button)
        self.gui_elements.append(select_level_button)
        self.gui_elements.append(game_options_button)
        self.gui_elements.append(exit_button)

    def gameLoop(self, task):

        #Compensate for inconsistent update intervals

        dt = globalClock.getDt()

        if self.GAME_MODE == MAIN_MENU:

            if not self.mode_initialized:

                self.buildMainMenu()

                self.mode_initialized = True

        if self.GAME_MODE == IN_GAME_MENU:

            if not self.mode_initialized:

                #Fog out background

                inGameMenuFogColor = (50, 150, 50)

                inGameMenuFog = Fog("inGameMenuFog")

                inGameMenuFog.setMode(Fog.MExponential)
                inGameMenuFog.setColor(*inGameMenuFogColor)
                inGameMenuFog.setExpDensity(.01)

                render.setFog(inGameMenuFog)

                self.buildInGameMenu()

                self.mode_initialized = True

        if self.GAME_MODE == PLAY:

            if not self.mode_initialized:

                props = WindowProperties()
                props.setCursorHidden(True) 
                base.win.requestProperties(props)

                self.last_mouse_x = self.win.getPointer(0).getX()
                self.last_mouse_y = self.win.getPointer(0).getY()

                self.mode_initialized = True

            if self.play_mode == TERRAIN:

                self.maintainTurrets()
                self.avatar.move(dt)

            elif self.play_mode == SPACE:

                self.asteroidManager.maintainAsteroidField(self.avatar.objectNP.getPos(), 
                                                           self.avatar.speed, dt)

            #Handle keyboard input

            self.avatar.handleKeys(self.keys, self.play_mode)

            ########## Mouse-based viewpoint rotation ##########

            mouse_pos = self.win.getPointer(0)

            current_mouse_x = mouse_pos.getX()
            current_mouse_y = mouse_pos.getY()

            #Side to side

            if self.play_mode == TERRAIN:

                mouse_shift_x = current_mouse_x - self.last_mouse_x
                self.last_mouse_x = current_mouse_x

                if current_mouse_x < 5 or current_mouse_x >= (self.win_center_x * 1.5):

                    base.win.movePointer(0, self.win_center_x, current_mouse_y)
                    self.last_mouse_x = self.win_center_x

                yaw_shift = -((mouse_shift_x) * Camera.ROT_RATE[0])

                self.avatar.yawRot += yaw_shift

                self.avatar.objectNP.setH(self.avatar.yawRot)

            #Up and down

            mouse_shift_y = current_mouse_y - self.last_mouse_y
            self.last_mouse_y = current_mouse_y

            if current_mouse_y < 5 or current_mouse_y >= (self.win_center_y * 1.5):

                base.win.movePointer(0, current_mouse_x, self.win_center_y)
                self.last_mouse_y = self.win_center_y

            pitch_shift = -((mouse_shift_y) * Camera.ROT_RATE[1])

            self.mainCamera.pitchRot += pitch_shift

            if self.mainCamera.pitchRot > Camera.FLEX_ROT_MAG[0]:

                self.mainCamera.pitchRot = Camera.FLEX_ROT_MAG[0]

            elif self.mainCamera.pitchRot < -Camera.FLEX_ROT_MAG[0]:

                self.mainCamera.pitchRot = -Camera.FLEX_ROT_MAG[0]

            xy_plane_cam_dist = Camera.AVATAR_DIST

            cam_x_adjust = xy_plane_cam_dist*sin(radians(self.avatar.yawRot))  
            cam_y_adjust = xy_plane_cam_dist*cos(radians(self.avatar.yawRot))
            cam_z_adjust = Camera.ELEVATION

            self.mainCamera.camObject.setH(self.avatar.yawRot)
            self.mainCamera.camObject.setP(self.mainCamera.pitchRot)

            self.mainCamera.camObject.setPos(self.avatar.objectNP.getX() + cam_x_adjust, self.avatar.objectNP.getY() - cam_y_adjust, 
                            self.avatar.objectNP.getZ() + cam_z_adjust)

            #Find collisions

            #self.cTrav.traverse(render)

            #print self.environ.getBounds()

        return Task.cont
예제 #11
0
class PinchTask(ShowBase, GripStateMachine):
    DATA_DIR = 'data'
    
    def __init__(self, id, session, hand, block, mode, wrist):
        ShowBase.__init__(self)
        GripStateMachine.__init__(self)
        base.disableMouse()
        wp = WindowProperties()
        wp.setSize(1920,1080)
        wp.setFullscreen(True)
        base.win.requestProperties(wp)

        self.sub_id = str(id)
        self.sess_id = str(session)
        self.hand = str(hand)
        self.block = str(block)
        self.mode = str(mode)
        self.wrist = str(wrist)
        
        self.prev_blk = os.path.join(self.DATA_DIR,'exp_1',self.sub_id,self.sess_id,self.wrist,self.hand,"B0")
        if self.wrist == 'pron':
            self.table = np.loadtxt('src/pinch_task/trialtable_pron.csv',dtype='str',delimiter=',',skiprows=1)
        elif self.wrist == 'flex':
            self.table = np.loadtxt('src/pinch_task/trialtable_flex.csv',dtype='str',delimiter=',',skiprows=1)
        else:
            raise NameError('Wrist position not found')

        try:
            self.prev_table = np.loadtxt(os.path.join(self.prev_blk, 'final_targets.csv'),dtype='str',delimiter=',',skiprows=1)
            indices = {}
            for i in range(self.prev_table.shape[0]):
                indices[self.prev_table[i,1]] = int(self.prev_table[i,0])-1
            for i in range(self.table.shape[0]):
                self.table[i,11] = self.prev_table[indices[self.table[i,1].strip()],11]
                self.table[i,12] = self.prev_table[indices[self.table[i,1].strip()],12]
                self.table[i,13] = self.prev_table[indices[self.table[i,1].strip()],13]
        except:
            print('Previous target file not found')
        
        self.table = np.array([[item.strip() for item in s] for s in self.table])

        ##################################################
        #only use rows relevant to this block
        #HARDCODED! NOTE IN LOG SHEET
        spec_table = []
        for i in range(self.table.shape[0]):
            if int(self.block)%4 == 0:
                if "(p)" in self.table[i,2]:
                    spec_table.append(self.table[i])
            elif int(self.block)%4 == 1:
                if "(t)" in self.table[i,2]:
                    spec_table.append(self.table[i])
            elif int(self.block)%4 == 2:
                if "(s)" in self.table[i,2]:
                    spec_table.append(self.table[i])
            elif int(self.block)%4 == 3:
                if "(t+s)" in self.table[i,2]:
                    spec_table.append(self.table[i])
        ###################################################
        self.table = np.array(spec_table)

        self.session_dir = os.path.join(self.DATA_DIR,'exp_1',self.sub_id,self.sess_id,self.wrist,self.hand)
        self.subjinfo = self.sub_id + '_' + self.sess_id + '_' + self.hand + '_log.yml'
        self.p_x,self.p_y,self.p_a = GET_POS(self.session_dir,self.subjinfo,self.hand,self.wrist)

        self.rotmat = ROT_MAT(self.p_a,self.hand)

        self.setup_text()
        self.setup_lights()
        self.setup_camera()
        
        self.trial_counter = 0
        self.load_models()
        self.load_audio()
        self.update_trial_command()
        self.countdown_timer = CountdownTimer()
        self.hold_timer = CountdownTimer()

        self.cTrav = CollisionTraverser()
        self.chandler = CollisionHandlerEvent()
        self.chandler.addInPattern('%fn-into-%in')
        self.chandler.addAgainPattern('%fn-again-%in')
        self.chandler.addOutPattern('%fn-outof-%in')
        self.attachcollnodes()

        taskMgr.add(self.read_data, 'read')
        for i in range(5):
            taskMgr.add(self.move_player, 'move%d' % i, extraArgs = [i], appendTask=True)
        taskMgr.add(self.log_data, 'log data')
        taskMgr.add(self.update_state, 'update_state', sort=1)

        self.accept('space', self.space_on)
        self.accept('escape', self.clean_up)
        self.space = False
        self.statenum = list()

        self.max_time = 20
        self.med_data = None

        self.grip_dir = os.path.join(self.DATA_DIR,'exp_1',self.sub_id,self.sess_id,self.wrist,self.hand,"B"+self.block)
        if not os.path.exists(self.grip_dir):
           print('Making new folders: ' + self.grip_dir)
           os.makedirs(self.grip_dir)

        self.dev = MpDevice(RightHand(calibration_files=['calibs/cal_mat_15.mat',  # thumb
                                               'calibs/cal_mat_31.mat',
                                               'calibs/cal_mat_8.mat',
                                               'calibs/cal_mat_21.mat',
                                               'calibs/cal_mat_13.mat'], clock=mono_clock.get_time))

        self.init_ser()

    ############
    #SET UP HUD#
    ############
    def setup_text(self):
        #OnscreenImage(parent=self.cam2dp, image='models/background.jpg')
        self.bgtext = OnscreenText(text='Not recording.', pos=(-0.8, 0.8),
                                 scale=0.08, fg=(0, 0, 0, 1),
                                 bg=(1, 1, 1, 1), frame=(0.2, 0.2, 0.8, 1),
                                 align=TextNode.ACenter)
        self.bgtext.reparentTo(self.aspect2d)

        self.dirtext = OnscreenText( pos=(-0.6, 0.65),
                                 scale=0.08, fg=(0, 0, 0, 1),
                                 bg=(1, 1, 1, 1), frame=(0.2, 0.2, 0.8, 1),
                                 align=TextNode.ACenter)
        self.dirtext.reparentTo(self.aspect2d)

    ##########################
    #SET UP SCENE AND PLAYERS#
    ##########################
    def setup_lights(self):
        pl = PointLight('pl')
        pl.setColor((1, 1, 1, 1))
        plNP = self.render.attachNewNode(pl)
        plNP.setPos(-10, -10, 10)
        self.render.setLight(plNP)
        pos = [[[0, 0, 50], [0, 0, -10]],
               [[0, -50, 0], [0, 10, 0]],
               [[-50, 0, 0], [10, 0, 0]]]
        for i in pos:
            dl = Spotlight('dl')
            dl.setColor((1, 1, 1, 1))
            dlNP = self.render.attachNewNode(dl)
            dlNP.setPos(*i[0])
            dlNP.lookAt(*i[1])
            dlNP.node().setShadowCaster(False)
            self.render.setLight(dlNP)

    def setup_camera(self):
        self.cam.setPos(0, -4, 12)
        self.cam.lookAt(0, 2, 0)
        self.camLens.setFov(90)

    def load_models(self):
        self.back_model = self.loader.loadModel('models/back')
        self.back_model.setScale(10, 10, 10)
        if self.hand == "Left":
            self.back_model.setH(90)
        self.back_model.reparentTo(self.render)

        self.player_offsets = [[self.p_x[0]-5, self.p_y[0]+3, 0], [self.p_x[1]-2.5, self.p_y[1]+4.5, 0], [self.p_x[2], self.p_y[2]+5, 0],
                                [self.p_x[3]+2.5, self.p_y[3]+4.5, 0], [self.p_x[4]+5, self.p_y[4]+3, 0]]
        self.p_col =[[0,0,250],[50,0,200],[125,0,125],[200,0,50],[250,0,0]]
        if self.hand == 'Left':
            self.p_col = self.p_col[::-1]

        self.players = list()
        self.contacts = list()        
        for counter, value in enumerate(self.player_offsets):
            self.players.append(self.loader.loadModel('models/target'))
            self.contacts.append(False)

            self.players[counter].setPos(*value)
            self.players[counter].setScale(0.2, 0.2, 0.2)
            self.players[counter].setColorScale(
                self.p_col[counter][0]/255, self.p_col[counter][1]/255, self.p_col[counter][2]/255, 1)
            self.players[counter].reparentTo(self.render)
            self.players[counter].show()

        self.target_select()

    def load_audio(self):
        self.pop = self.loader.loadSfx('audio/Blop.wav')
        self.buzz = self.loader.loadSfx('audio/Buzzer.wav')


    ############################
    #SET UP COLLISION MECHANICS#
    ############################
    def attachcollnodes(self):
        for i in range(5):
            self.fromObject = self.players[i].attachNewNode(CollisionNode('colfromNode'+str(i)))
            self.fromObject.node().addSolid(CollisionSphere(0,0,0,1))
            self.cTrav.addCollider(self.fromObject, self.chandler)

        for i in range(5):
            self.accept('colfromNode%d-into-colintoNode' % i, self.collide1,[i])
            self.accept('colfromNode%d-again-colintoNode' % i, self.collide2,[i])
            self.accept('colfromNode%d-outof-colintoNode' % i, self.collide3,[i])

    def collide1(self,f,collEntry):
        if f in self.highlighted_indices:
            self.players[f].setColorScale(0,1,0,0)
            self.tar.setColorScale(0.2,0.2,0.2,1)
            self.tar.setAlphaScale(0.7)
            self.contacts[f] = True
            taskMgr.doMethodLater(self.delay,self.too_long,'too_long%d' % f,extraArgs = [f])
            self.sendsig(1,f,100)
                
    def collide2(self,f,collEntry):
        if f in self.highlighted_indices:
            dist = np.sqrt(self.distances[f][1]^2+self.distances[f][2]^2+self.distances[f][3]^2)
            self.sendsig(2,f,int(10/dist)+100)
        for i in self.highlighted_indices:
            if self.contacts[i] == False:
                return
        taskMgr.remove('too_long%d' % f)

    def collide3(self,f,collEntry):
        taskMgr.remove('too_long%d' % f)
        self.reset_fing(f)
        self.tar.setColorScale(0.1,0.1,0.1,1)
        self.tar.setAlphaScale(0.7)

    def too_long(self,f):
        self.reset_fing(f)
        self.tar.setColorScale(0.5,0.2,0.2,1)
        self.tar.setAlphaScale(0.7)

    def reset_fing(self,f):
        self.players[f].setColorScale(
                self.p_col[f][0]/255, self.p_col[f][1]/255, self.p_col[f][2]/255, 1)
        self.contacts[f] = False
        self.sendsig(3,f,0)

    ###############
    #TARGET THINGS#
    ###############
    def show_target(self):
        self.target_select()
        self.intoObject = self.tar.attachNewNode(CollisionNode('colintoNode'))

        if self.table[self.trial_counter,7] == "sphere":
            self.intoObject.node().addSolid(CollisionSphere(0,0,0,1))
        elif self.table[self.trial_counter,7] == "cylinder":
            self.intoObject.node().addSolid(CollisionTube(0,0,-2,0,0,2,1))
        else:
            raise NameError("No such collision type")

        self.tar.show()

        #hide players not related to target
        for i in range(5):
            if i not in self.highlighted_indices:
                self.players[i].hide()
        
    def target_select(self):
        self.tgtscx=float(self.table[self.trial_counter,14])
        self.tgtscy=float(self.table[self.trial_counter,15])
        self.tgtscz=float(self.table[self.trial_counter,16])
        tgttsx=float(self.table[self.trial_counter,11])
        tgttsy=float(self.table[self.trial_counter,12])
        tgttsz=float(self.table[self.trial_counter,13])
        tgtrx=float(self.table[self.trial_counter,17])
        tgtry=float(self.table[self.trial_counter,18])
        tgtrz=float(self.table[self.trial_counter,19])
        if self.hand == 'Left':
            tgttsx *= -1
            tgtrx *= -1

        self.static_task = (str(self.table[self.trial_counter,5]) == "True")
        self.target_model = str(self.table[self.trial_counter,6])
        self.highlighted_indices=[int(s)-1 for s in self.table[self.trial_counter,4].split(' ')]
        if self.hand == 'Left':
            self.highlighted_indices=[4-i for i in self.highlighted_indices]

        #NOTE:this position finding is present in all three tasks
        #     it is somewhat hacky and can be improved upon
        self.tgtposx = np.mean(np.asarray(self.player_offsets)[self.highlighted_indices][[-2,-1],0]) + tgttsx
        self.tgtposy = np.mean(np.asarray(self.player_offsets)[self.highlighted_indices][[0,1],1]) + tgttsy
        if len(self.highlighted_indices) > 3: #for sphere, return to just average of all fingers
            self.tgtposx = np.mean(np.asarray(self.player_offsets)[self.highlighted_indices][:,0]) + tgttsx
            #self.tgtposy = np.mean(np.asarray(self.player_offsets)[self.highlighted_indices][:,1])
        self.tgtposz = np.mean(np.asarray(self.player_offsets)[self.highlighted_indices][:,2]) + tgttsz

        self.tar = self.loader.loadModel(self.target_model)
        self.tar.setScale(self.tgtscx,self.tgtscy,self.tgtscz)
        self.tar.setPos(self.tgtposx,self.tgtposy,self.tgtposz)
        self.tar.setHpr(tgtrx,tgtry,tgtrz)
        self.tar.setColorScale(0.1, 0.1, 0.1, 1)
        self.tar.setAlphaScale(0.7)
        self.tar.setTransparency(TransparencyAttrib.MAlpha) 
        self.tar.reparentTo(self.render)
        self.tar.hide()

        self.delay=float(self.table[self.trial_counter,8])
        self.loc_angle=math.radians(float(self.table[self.trial_counter,9]))
        self.invf=float(self.table[self.trial_counter,10])
        
        self.distances = [[0,0,0],[0,0,0],[0,0,0],[0,0,0],[0,0,0]]

    ##############
    #MOVE FINGERS#
    ##############
    def read_data(self,task):
        error, data = self.dev.read()
        if data is not None:
            data *= 0.001
            self.ts = data.time
            data = np.dot(data,self.rotmat)
            self.data = data
            if self.med_data is None:
                self.med_data = np.median(data, axis=0)

            if self.space:
                self.statenum.extend(([self.checkstate()])*len(data.time))
                
        return task.cont
        
    def move_player(self,p,task):
        if self.data is not None :
            k = p*3
            new_x = 10*np.mean(self.data[-1,k]) + self.player_offsets[p][0] - 10*self.med_data[k]
            new_y = 10*np.mean(self.data[-1,k + 1]) + self.player_offsets[p][1] - 10*self.med_data[k + 1]
            new_z = 10*np.mean(self.data[-1,k + 2]) + self.player_offsets[p][2] - 10*self.med_data[k + 2]

            #make sure digits do not cross each other
            if ((p in range(1,3) and p+1 in self.highlighted_indices and new_x > self.players[p+1].getX())
                or (p in range(2,4) and p-1 in self.highlighted_indices and new_x < self.players[p-1].getX())):
                    new_x = self.players[p].getX()
            
            #make sure digits do not cross into target
            if self.space == True and p in self.highlighted_indices:
                self.distances[p][0] = new_x - self.tar.getX()
                self.distances[p][1] = new_y - self.tar.getY()
                self.distances[p][2] = new_z - self.tar.getZ()
                self.check_pos(p)
                
            self.players[p].setPos(new_x, new_y, new_z)
            
        return task.cont
    
    def check_pos(self,p):
        if (abs(self.distances[p][0]) < self.invf*self.tgtscx
            and abs(self.distances[p][1]) < self.invf*self.tgtscy
            and abs(self.distances[p][2]) < self.invf*self.tgtscz):
                self.too_long(p)

    ##################
    #CHECK COMPLETION#
    ##################
    def close_to_target(self):
        for i in self.highlighted_indices:
            if self.contacts[i] == False:
                return False

        if not self.check_angle():
            self.tar.setColorScale(0.1,0.1,0.1,1)
            self.tar.setAlphaScale(0.7)
            return False

        self.tar.setColorScale(0,1,1,1)
        return True

    def check_hold(self):
        if not self.close_to_target():
            self.hold_timer.reset(0.5)
            return False
        return self.hold_timer.elapsed() < 0

    def check_angle(self):
        #hardcoded condition may be able to be assimilated into old angle method somehow
        if self.table[self.trial_counter,1] == 'pts':
            vec = np.subtract(self.players[self.highlighted_indices[1]].getPos(), self.players[self.highlighted_indices[0]].getPos())
            xvec = [1,0,0]
            if self.hand == 'Left':
                xvec = [-1,0,0]
            print(math.degrees(math.acos(np.dot(vec,xvec)/(np.linalg.norm(vec)*np.linalg.norm(xvec)))))
            if math.acos(np.dot(vec,xvec)/(np.linalg.norm(vec)*np.linalg.norm(xvec))) < self.loc_angle:
                return True
            else: return False
        thumbindx = 0
        if self.hand == "Left": thumbindx = 4
        for i in self.highlighted_indices:
            if i == thumbindx:
                continue
            th = self.distances[thumbindx]
            fg = self.distances[i]
            if math.acos(np.dot(th,fg)/(np.linalg.norm(th)*np.linalg.norm(fg))) > self.loc_angle:
                return True
        return False

    def adjust_targets(self):
        #no adjustment if more than 2 fingers or position is prone
        if len(self.highlighted_indices) > 2 or self.wrist == 'pron':
            return

        xadj,yadj,zadj = np.mean(np.asarray(self.distances)[self.highlighted_indices],0)
        #yadj = np.mean(np.asarray(self.distances)[self.highlighted_indices][1])
        #zadj = np.mean(np.asarray(self.distances)[self.highlighted_indices][2])

        #do adjustment on all tasks with same name
        if self.hand == 'Left':
            xadj = -xadj
        for i in range(self.trial_counter+1,self.table.shape[0]):
            if self.table[i,1] == self.table[self.trial_counter,1]:
                self.table[i,11] = float(self.table[i,11]) + xadj
                self.table[i,12] = float(self.table[i,12]) + yadj
                self.table[i,13] = float(self.table[i,13]) + zadj


    #########
    #LOGGING#
    #########
    def play_success(self):
        if int(self.block) == 0:
            self.adjust_targets()
        self.pop.play()
        self.tar.hide()
        self.highlighted_indices = [0,1,2,3,4]

    def log_text(self):
        self.bgtext.setText('Now logging...')

    def log_data(self, task):
        if (self.trial_counter + 1) <= self.table.shape[0]:
            if self.space:
                self.log_file_name = os.path.join(self.grip_dir,
                                          self.sub_id+"_"+self.sess_id+"_"+self.hand+"_"+
                                              str(self.table[self.trial_counter,1])+"_"+str(self.table[self.trial_counter,0])+".csv" )
                self.movvars = np.column_stack((self.ts, self.statenum, self.data))
                self.statenum = []
                if self.mode=='task':
                    with open(self.log_file_name, 'ab') as f:
                        np.savetxt(f, self.movvars, fmt='%10.5f', delimiter=',')
            return task.cont
        else:
            pass

    def stoplog_text(self):
        self.dirtext.clearText()
        self.bgtext.setText('Done logging!')
        for i in range(5):
            self.players[i].show()

    #######
    #RESET#
    #######
    def delete_file(self):
        if (self.trial_counter + 1) <= self.table.shape[0]:
            self.log_file_name = os.path.join(self.grip_dir,
                                      self.sub_id+"_"+self.sess_id+"_"+self.hand+"_"+
                                          str(self.table[self.trial_counter,1])+"_"+str(self.table[self.trial_counter,0])+".csv" )
            try:
                os.remove(self.log_file_name)
            except OSError:
                pass
        else:
            pass

    def reset_baseline(self):
       self.med_data = None
                   
    def reset_keyboard_bool(self):
        self.space = False

    def hide_target(self):
        self.tar.hide()
        self.intoObject.removeNode()
        self.imageObject.destroy()

    def update_trial_command(self):
        self.dirtext.setText(str(self.table[self.trial_counter,2]))
        if self.hand == 'Left':
            xfac = -0.25
        else:
            xfac = 0.25
        self.imageObject = OnscreenImage(image = str(self.table[self.trial_counter,3]),scale=(xfac,0.25,0.25),pos=(-1.2, 0, 0.3))

    def increment_trial_counter(self):
        self.trial_counter += 1
        self.update_trial_command()

    ########
    #TIMERS#
    ########
    def start_trial_countdown(self):
        self.countdown_timer.reset(self.max_time)

    def start_hold_countdown(self):
        self.hold_timer.reset(0.5)

    def start_post_countdown(self):
        self.countdown_timer.reset(2)

    def time_elapsed(self):
        return self.countdown_timer.elapsed() < 0

    #########
    #MACHINE#
    #########
    def update_state(self, task):
        self.step()
        return task.cont

    def wait_for_space(self):
        return self.space

    def space_on(self):
        self.space = True

    #####
    #END#
    #####
    def trial_counter_exceeded(self):
        return (self.trial_counter+1) > self.table.shape[0]-1

    def clean_up(self):
        #write last known positions to 'final_targets' file
        f = open('src/pinch_task/trialtable_flex.csv')
        header = f.readline().rstrip()
        np.savetxt(self.grip_dir + '/final_targets.csv',self.table,fmt='%s',header = header, delimiter=',')
        f.close()
        sys.exit()

    ########
    #SERIAL#
    ########
    def init_ser(self):
        #CONNECT TO HAPTIC DEVICE
        ports = list_ports.comports()
        mydev = next((p.device for p in ports if p.pid == 1155))
        self.ser = serial.Serial(mydev,9600,timeout=.1)

    def sendsig(self,signal,finger,intensity):
        #would read from table, but table not available yet
        if intensity > 255:
            intensity = 255
        dur_int = [signal,finger,intensity]
        data = struct.pack('3B',*dur_int)
        self.ser.write(data)
class DonkeyKong(ShowBase):
    def __init__(self):
        super().__init__(self)
        self.angle = 0
        self.taskMgr.add(self.setup, "setup")
        self.taskMgr.add(self.update, "update")

        self.scene = self.loader.loadModel('models/DKSet')
        self.scene.reparentTo(self.render)

        self.arcadeTexture = self.loader.loadTexture('models/dk-arcade.png')
        self.scene.setTexture(self.arcadeTexture)
        self.scene.setTransparency(1)

        self.blocksTexture = self.loader.loadTexture('models/block.png')
        self.stairsTexture = self.loader.loadTexture('models/stairs.png')

        #messenger.toggleVerbose()

    def setup(self, task):
        lens = OrthographicLens()
        lens.setFilmSize(25, 20)
        base.camNode.setLens(lens)

        self.player = self.scene.attachNewNode("Player")

        self.marioGfx = self.scene.find('root/mario')
        self.marioGfx.reparentTo(self.player)

        self.jumpAvailable = False
        self.gravity = -.5
        self.verticalTime = 0
        self.v0 = 0
        self.floorZ = 0
        self.onStairs = False
        self.jumpCounter = 1
        # input setup

        self.input = {
            'up': False,
            'down': False,
            'left': False,
            'right': False,
            'space': False
        }

        key_list = ['up', 'down', 'left', 'right']
        for k in key_list:
            self.accept(f'raw-arrow_{k}', self.buildPress(k))
            self.accept(f'raw-arrow_{k}-up', self.buildRelease(k))

        self.accept(f'raw-space', self.buildPress('space'))
        self.accept(f'raw-space-up', self.buildRelease('space'))

        # collision set up
        base.cTrav = CollisionTraverser()
        self.collisionHandlerEvent = CollisionHandlerEvent()
        self.collisionHandlerEvent.addInPattern('into-%in')
        self.collisionHandlerEvent.addOutPattern('outof-%in')

        ray = CollisionSegment(0, 0, 0, 0, 0, -.6)
        cNodePath = self.player.attachNewNode(CollisionNode('marioRay'))
        cNodePath.node().addSolid(ray)
        cNodePath.node().setIntoCollideMask(0x03)
        cNodePath.node().setFromCollideMask(0x03)
        cNodePath.show()
        base.cTrav.addCollider(cNodePath, self.collisionHandlerEvent)

        self.floor1 = self.createSquareCollider(-1.8, -5.5, 9.3, .5, 'floor0',
                                                'floor1HitBox', 'Floor1',
                                                self.enableJump,
                                                self.disableJump,
                                                self.blocksTexture, 0x1)
        self.floor2 = self.createSquareCollider(2.08, -2.5, 8.0, .5, 'floor1',
                                                'floor2HitBox', 'Floor2',
                                                self.enableJump,
                                                self.disableJump,
                                                self.blocksTexture, 0x1)
        self.floor3_1 = self.createSquareCollider(3.6, 0.5, 3.8, .5, 'floor2',
                                                  'floor3_1HitBox', 'Floor3_1',
                                                  self.enableJump,
                                                  self.disableJump,
                                                  self.blocksTexture, 0x1)
        self.floor3_2 = self.createSquareCollider(-6.3, 0.5, 5, .5, 'pCube4',
                                                  'floor3_2HitBox', 'Floor3_2',
                                                  self.enableJump,
                                                  self.disableJump,
                                                  self.blocksTexture, 0x1)
        self.floor4 = self.createSquareCollider(1.8, 3.5, 8.0, .5, 'floors',
                                                'floor4HitBox', 'Floor4',
                                                self.enableJump,
                                                self.disableJump,
                                                self.blocksTexture, 0x1)

        self.topStair = self.createSquareCollider(
            -6.8, 3.5, 0.5, 2.5, 'topstair', 'topStairHitBox', 'TopStair',
            self.enableStairs, self.disableStairs, self.stairsTexture, 0x2)
        self.middleStair = self.createSquareCollider(
            -0.86, 0.1, 0.5, 2.5, 'middlestair', 'middleStairHitBox',
            'MiddleStair', self.enableStairs, self.disableStairs,
            self.stairsTexture, 0x2)
        self.bottomStair = self.createSquareCollider(
            -6.8, -2.5, 0.5, 2.5, 'bottomstair', 'bottomStairHitBox',
            'BottomStair', self.enableStairs, self.disableStairs,
            self.stairsTexture, 0x2)

        #self.createInvisibleSquareCollider(0,0,8,3,"NewCollision","NewNode")
        #self.createInvisibleSquareCollider(-6,0,4,5,"NewCollisio2","NewNode2")
        base.cTrav.showCollisions(self.render)

        # self.player.setPos(3,0,-3.5)
        self.player.setPos(-8, 0, -1.5)
        return Task.done

    def enableJump(self, evt):
        print(f'IN----> {evt}')
        self.floorZ = evt.getIntoNodePath().node().getParent(
            0).getTransform().getPos().z + 1
        self.jumpAvailable = True

    def disableJump(self, evt):
        print(f'Out----> {evt}')
        self.jumpAvailable = False

    def enableStairs(self, evt):
        print(f'IN----> {evt}')
        self.onStairs = True

    def disableStairs(self, evt):
        print(f'Out----> {evt}')
        self.onStairs = False

    def createSquareCollider(self, px, pz, w, h, modelName, collisionNodeName,
                             nodeName, intoFunction, outFunction, texture,
                             mask):
        obj = self.scene.attachNewNode(nodeName)
        hitBox = CollisionBox(Point3(0, 0, 0), w, 5, h)
        cNodePath = obj.attachNewNode(CollisionNode(collisionNodeName))
        cNodePath.node().addSolid(hitBox)
        cNodePath.node().setIntoCollideMask(mask)
        cNodePath.node().setFromCollideMask(mask)
        #cNodePath.show()
        base.cTrav.addCollider(cNodePath, self.collisionHandlerEvent)

        self.scene.find(f'root/{modelName}').reparentTo(obj)
        obj.setPos(px, 0, pz)
        obj.setTexture(texture)

        self.accept(f'into-{collisionNodeName}', intoFunction)
        self.accept(f'outof-{collisionNodeName}', outFunction)

        return obj

    def createInvisibleSquareCollider(self, px, pz, w, h, collisionNodeName,
                                      nodeName, mask):
        obj = self.scene.attachNewNode(nodeName)
        hitBox = CollisionBox(Point3(0, 0, 0), w, 5, h)
        cNodePath = obj.attachNewNode(CollisionNode(collisionNodeName))
        cNodePath.node().addSolid(hitBox)
        cNodePath.node().setIntoCollideMask(mask)
        cNodePath.node().setFromCollideMask(mask)
        cNodePath.show()
        base.cTrav.addCollider(cNodePath, self.collisionHandlerEvent)
        obj.setPos(px, 0, pz)

    def buildPress(self, key):
        def pressKey():
            self.input[key] = True

        return pressKey

    def buildRelease(self, key):
        def releaseKey():
            self.input[key] = False

        return releaseKey

    def applyMove(self):

        mv = Vec3(0, 0, 0)
        p = self.player.getPos()

        if (self.input["right"]):
            mv.x = -.1

        if (self.input["left"]):
            mv.x = .1
        """
        if( self.input["space"]):
            playerPos.z += .1
            
        if( self.input["down"]):
            playerPos.z -= .1
        """

        if (self.jumpAvailable and not self.onStairs):
            self.jumpCounter = 1
            self.verticalTime = 0
            self.v0 = 0
            p.z = self.floorZ
            if (self.input["space"]):
                self.v0 = .165
                self.jumpAvailable = False

        if (not self.jumpAvailable and not self.onStairs):
            self.verticalTime += globalClock.getDt()
            mv.z = self.v0 + self.gravity * self.verticalTime

        if (self.onStairs):
            self.jumpCounter = 0
            self.v0 = 0
            if (self.input["down"]):
                mv.z = -.1
            if (self.input["up"]):
                mv.z = .1

        if (not self.onStairs):
            if (not self.jumpAvailable):
                if (self.input["space"] and self.jumpCounter == 0):
                    self.v0 = .165
                    self.jumpAvailable = False
                    self.jumpCounter = 1

        p.x += mv.x
        p.z += mv.z

        self.player.setPos(p)

        # hacer que se pueda agarrar el martillo, cuando suceda : self.marioGfx.setSx(self.player  , -1)
        # self.hammer = self.createSquareCollider(6,1.5,.5,.5,'hammer','hammerHitbox', 'hammer', self.enableHammer, self.disableHammer, self.arcadeTexture, 0x02)

    def update(self, task):
        self.camera.setPos(0, 35, 0)
        self.camera.lookAt(self.scene)

        self.applyMove()

        return Task.cont
예제 #13
0
파일: player.py 프로젝트: grimfang/owp_ajaw
class Player(FSM, DirectObject):
    NormalMode = "Normal"
    FightMode = "Fight"

    GAMEPADMODE = "Gamepad"
    MOUSEANDKEYBOARD = "MouseAndKeyboard"

    def __init__(self):
        FSM.__init__(self, "FSM-Player")
        random.seed()

        #
        # PLAYER CONTROLS AND CAMERA
        #
        self.player = Actor(
            "Character",
            {
                "Idle": "Character-Idle",
                "Run": "Character-Run",
                "Activate": "Character-Activate",
                "Death": "Character-Death",
                "Jump": "Character-Jump",
                "Hit": "Character-Hit",
                "Fight_Attack": "Character-FightAttack",
                "Fight_Idle": "Character-FightIdle",
                "Fight_Left": "Character-FightLeft",
                "Fight_Right": "Character-FightRight",
            },
        )
        self.player.setBlend(frameBlend=True)
        # the initial cam distance
        self.fightCamDistance = 3.0
        # the next two vars will set the min and max distance the cam can have
        # to the node it is attached to
        self.maxCamDistance = 4.0
        self.minCamDistance = 1.2
        # the initial cam distance
        self.camDistance = (self.maxCamDistance - self.minCamDistance) / 2.0 + self.minCamDistance
        # the next two vars set the min and max distance on the Z-Axis to the
        # node the cam is attached to
        self.maxCamHeightDist = 3.0
        self.minCamHeightDist = 1.5
        # the average camera height
        self.camHeightAvg = (self.maxCamHeightDist - self.minCamHeightDist) / 2.0 + self.minCamHeightDist
        # an invisible object which will fly above the player and will be used to
        # track the camera on it
        self.camFloater = NodePath(PandaNode("playerCamFloater"))
        self.camFloater.setPos(0, 0, 1.5)
        self.camFloater.reparentTo(self.player)
        # screen sizes
        self.winXhalf = base.win.getXSize() / 2
        self.winYhalf = base.win.getYSize() / 2
        # Interval for the jump animation
        self.jumpInterval = None
        self.jumpstartFloater = NodePath(PandaNode("jumpstartFloater"))
        self.jumpstartFloater.reparentTo(render)
        self.deathComplete = None
        # Joystick/Gamepad support
        self.hasJoystick = False
        if gamepadSupport:
            # initialize controls
            joysticks = [pygame.joystick.Joystick(x) for x in range(pygame.joystick.get_count())]
            if len(joysticks) > 0:
                self.mainJoystick = joysticks[0]
                self.mainJoystick.init()
                self.hasJoystick = True

        #
        # WEAPONS AND ACCESSORIES
        #
        self.RightHandAttach = self.player.exposeJoint(None, "modelRoot", "HandAttach_R")
        self.spear = loader.loadModel("Spear")
        self.spear.setP(90)
        self.spear.setR(180)
        self.spear.reparentTo(self.RightHandAttach)
        self.LeftHandAttach = self.player.exposeJoint(None, "modelRoot", "HandAttach_L")
        self.shield = loader.loadModel("Shield")
        self.shield.setZ(0.05)
        self.shield.setH(-90)
        self.shield.reparentTo(self.LeftHandAttach)

        #
        # PLAYER COLLISION DETECTION AND PHYSICS
        #
        self.playerSphere = CollisionSphere(0, 0, 0.8, 0.7)
        self.playerCollision = self.player.attachNewNode(CollisionNode("playerCollision"))
        self.playerCollision.node().addSolid(self.playerSphere)
        base.pusher.addCollider(self.playerCollision, self.player)
        base.cTrav.addCollider(self.playerCollision, base.pusher)
        # The foot collision checks
        self.footRay = CollisionRay(0, 0, 0, 0, 0, -1)
        self.playerFootRay = self.player.attachNewNode(CollisionNode("playerFootCollision"))
        self.playerFootRay.node().addSolid(self.footRay)
        self.playerFootRay.node().setIntoCollideMask(0)
        self.lifter = CollisionHandlerFloor()
        self.lifter.addCollider(self.playerFootRay, self.player)
        self.lifter.setMaxVelocity(5)
        base.cTrav.addCollider(self.playerFootRay, self.lifter)
        # a collision segment slightly in front of the player to check for jump ledges
        self.jumpCheckSegment = CollisionSegment(0, -0.2, 0.5, 0, -0.2, -2)
        self.playerJumpRay = self.player.attachNewNode(CollisionNode("playerJumpCollision"))
        self.playerJumpRay.node().addSolid(self.jumpCheckSegment)
        self.playerJumpRay.node().setIntoCollideMask(0)
        self.jumper = CollisionHandlerEvent()
        self.jumper.addOutPattern("%fn-out")
        base.cTrav.addCollider(self.playerJumpRay, self.jumper)
        # a collision segment to check attacks
        self.attackCheckSegment = CollisionSegment(0, 0, 1, 0, -1.3, 1)
        self.playerAttackRay = self.player.attachNewNode(CollisionNode("playerAttackCollision"))
        self.playerAttackRay.node().addSolid(self.attackCheckSegment)
        self.playerAttackRay.node().setIntoCollideMask(0)
        self.attackqueue = CollisionHandlerQueue()
        base.cTrav.addCollider(self.playerAttackRay, self.attackqueue)

        #
        # SOUNDEFFECTS
        #
        self.footstep = loader.loadSfx("Footstep.ogg")
        self.footstep.setLoop(True)
        self.footstep.setPlayRate(1.5)
        self.footstep.setVolume(0.5)
        self.spearAttackSfx = loader.loadSfx("SpearAttack.ogg")
        self.spearAttackSfx.setVolume(0.5)

    #
    # START/STOP
    #
    def start(self, startPoint):
        self.player.setPos(startPoint.getPos())
        self.player.setHpr(startPoint.getHpr())
        self.player.reparentTo(render)
        self.jumpstartFloater.setPos(self.player.getPos())

        self.keyMap = {"horizontal": 0, "vertical": 0}

        self.health = 3
        self.trackedEnemy = None
        # this mode will be used to determine in which move mode the player currently is
        self.mode = Player.NormalMode
        # the initial cam height
        self.camHeight = self.camHeightAvg
        # a time to keep the cam zoom at a specific speed independent of
        # current framerate
        self.camElapsed = 0.0
        self.mouseSpeedX = 15.0 * base.mouseSensitivity
        self.mouseSpeedY = 0.2 * base.mouseSensitivity
        self.speed = 1.0

        self.camCenterEvents = ["centerCam", "home", "q"]
        self.camZoomInEvents = ["zoomIn", "+", "wheel_up"]
        self.camZoomOutEvents = ["zoomOut", "-", "wheel_down"]
        self.actionEvents = ["doAction", "enter", "e"]

        self.accept("arrow_left", self.setKey, ["horizontal", 1])
        self.accept("arrow_right", self.setKey, ["horizontal", -1])
        self.accept("arrow_up", self.setKey, ["vertical", -1])
        self.accept("arrow_down", self.setKey, ["vertical", 1])
        self.accept("arrow_left-up", self.setKey, ["horizontal", 0])
        self.accept("arrow_right-up", self.setKey, ["horizontal", 0])
        self.accept("arrow_up-up", self.setKey, ["vertical", 0])
        self.accept("arrow_down-up", self.setKey, ["vertical", 0])
        self.accept("a", self.setKey, ["horizontal", 1])
        self.accept("d", self.setKey, ["horizontal", -1])
        self.accept("w", self.setKey, ["vertical", -1])
        self.accept("s", self.setKey, ["vertical", 1])
        self.accept("a-up", self.setKey, ["horizontal", 0])
        self.accept("d-up", self.setKey, ["horizontal", 0])
        self.accept("w-up", self.setKey, ["vertical", 0])
        self.accept("s-up", self.setKey, ["vertical", 0])
        for event in self.camCenterEvents:
            self.acceptOnce(event, self.center)
        for event in self.camZoomInEvents:
            self.acceptOnce(event, self.zoom, [True])
        for event in self.camZoomOutEvents:
            self.acceptOnce(event, self.zoom, [False])
        for event in self.actionEvents:
            self.acceptOnce(event, self.request, ["Action"])
        self.accept("ActionDone", self.request, ["Idle"])

        self.accept("playerJumpCollision-out", self.jump)

        taskMgr.add(self.move, "task_movement", priority=-10)
        taskMgr.add(self.updateCam, "task_camActualisation", priority=-4)

        if self.hasJoystick:
            taskMgr.add(self.gamepadLoop, "task_gamepad_loop", priority=-5)

        camera.setPos(self.player, 0, self.camDistance, self.camHeightAvg)

        self.hasJumped = False
        self.isActionmove = False

        self.request("Idle")

    def stop(self):
        taskMgr.remove("task_movement")
        taskMgr.remove("task_camActualisation")
        taskMgr.remove("task_gamepad_loop")
        self.ignoreAll()
        self.player.hide()

    def cleanup(self):
        self.stop()
        if self.deathComplete is not None:
            self.deathComplete.finish()
        if self.jumpInterval is not None:
            self.jumpInterval.finish()
        self.spear.removeNode()
        self.shield.removeNode()
        self.player.cleanup()
        self.player.removeNode()
        self.jumpstartFloater.removeNode()
        self.camFloater.removeNode()

    #
    # BASIC FUNCTIONS
    #
    def die(self):
        self.health -= 1
        base.messenger.send("setHealth", [self.health])
        self.request("Death")

    def heal(self):
        if self.health >= 3:
            return
        self.health += 1
        base.messenger.send("setHealth", [self.health])

    def hit(self):
        self.health -= 1
        base.messenger.send("setHealth", [self.health])
        if self.health == 0:
            self.request("Death")
        else:
            self.request("Hit")

    def resetPlayerPos(self):
        self.player.setPos(self.jumpstartFloater.getPos())
        self.jumper.clear()
        self.request("Idle")

    def gameOver(self):
        base.messenger.send("GameOver", ["loose"])

    def enterFightMode(self, trackedEnemy):
        self.trackedEnemy = trackedEnemy
        self.mode = Player.FightMode
        base.messenger.send("EnterFightMode")

    def exitFightMode(self):
        self.trackedEnemy = None
        self.mode = Player.NormalMode
        base.messenger.send("ExitFightMode")

    def gamepadLoop(self, task):
        joymap = {0: "doAction", 5: "centerCam", 6: "zoomIn", 4: "zoomOut", 9: "escape"}
        for event in pygame.event.get():
            for button in range(self.mainJoystick.get_numbuttons()):
                if button in joymap and self.mainJoystick.get_button(button):
                    base.messenger.send(joymap[button])
            if event.type == pygame.JOYAXISMOTION:
                for axis in range(self.mainJoystick.get_numaxes()):
                    axisChange = 0.0
                    axisChange = self.mainJoystick.get_axis(axis)
                    if axis == 0:
                        self.setKey("horizontal", -axisChange)
                    if axis == 1:
                        self.setKey("vertical", axisChange)
        return task.cont

    def setAnimationSpeed(self, requestedState):
        if requestedState == "Run":
            self.player.setPlayRate(3 * self.speed, "Run")
        elif requestedState == "RunReverse":
            self.player.setPlayRate(-3 * self.speed, "Run")
        elif requestedState == "FightLeft":
            self.player.setPlayRate(2 * self.speed, "Fight_Left")
        elif requestedState == "FightRight":
            self.player.setPlayRate(2 * self.speed, "Fight_Right")

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

    def move(self, task):
        dt = globalClock.getDt()
        resetMouse = False

        def resetMouse():
            if base.controlType == Player.MOUSEANDKEYBOARD:
                base.win.movePointer(0, self.winXhalf, self.winYhalf)

        if self.player.getAnimControl("Hit").isPlaying() or self.player.getAnimControl("Death").isPlaying():
            resetMouse()
            return task.cont
        if self.deathComplete is not None:
            if self.deathComplete.isPlaying():
                resetMouse()
                return task.cont
        if self.jumpInterval is not None:
            if self.jumpInterval.isPlaying():
                resetMouse()
                return task.cont
        if self.isActionmove:
            resetMouse()
            return task.cont

        if self.mode == Player.NormalMode:
            self.__normalMove(dt)
        else:
            self.__fightMove(dt)
        return task.cont

    def __normalMove(self, dt):
        requestState = "Idle"
        move = False
        if self.keyMap["horizontal"] != 0:
            requestState = "Run"
            move = True
        if self.keyMap["vertical"] != 0:
            requestState = "Run"
            move = True
        if move and base.controlType == Player.GAMEPADMODE:
            movementVec = Vec3(self.keyMap["horizontal"], self.keyMap["vertical"], 0)
            self.speed = max(abs(self.keyMap["horizontal"]), abs(self.keyMap["vertical"]))
            angle = math.atan2(-movementVec.getX(), movementVec.getY())
            rotation = angle * (180.0 / math.pi)
            self.player.setH(camera, rotation)
            self.player.setP(0)
            self.player.setR(0)
            self.player.setPos(self.player, (0, -2 * self.speed * dt, 0))
        elif base.controlType == Player.MOUSEANDKEYBOARD:
            if not base.mouseWatcherNode.hasMouse():
                return
            self.pointer = base.win.getPointer(0)
            mouseX = self.pointer.getX()
            mouseY = self.pointer.getY()

            if base.win.movePointer(0, self.winXhalf, self.winYhalf):
                z = camera.getZ() + (mouseY - self.winYhalf) * self.mouseSpeedY * dt
                camera.setZ(z)

                h = self.player.getH() - (mouseX - self.winXhalf) * self.mouseSpeedX * dt
                if h < -360:
                    h = 360
                elif h > 360:
                    h = -360
                self.player.setH(h)
                if move:
                    self.player.setPos(
                        self.player, (2 * dt * self.keyMap["horizontal"], 2 * dt * self.keyMap["vertical"], 0)
                    )
                self.center()
        if self.state != requestState:
            self.request(requestState)
        self.setAnimationSpeed(requestState)

    def __fightMove(self, dt):
        if self.trackedEnemy == None:
            return
        requestState = "Idle"
        self.player.lookAt(self.trackedEnemy)
        self.player.setH(self.player, 180)
        if self.keyMap["horizontal"] > 0:
            self.player.setX(self.player, 2 * self.speed * dt)
            requestState = "FightLeft"
        elif self.keyMap["horizontal"] < 0:
            self.player.setX(self.player, -2 * self.speed * dt)
            requestState = "FightRight"
        elif self.keyMap["vertical"] < 0:
            self.player.setY(self.player, -2 * self.speed * dt)
            requestState = "Run"
        elif self.keyMap["vertical"] > 0:
            self.player.setY(self.player, 2 * self.speed * dt)
            requestState = "RunReverse"
        if self.state != requestState:
            self.request(requestState)
        self.setAnimationSpeed(requestState)

    def jump(self, extraArg):
        intoName = extraArg.getIntoNode().getName().lower()
        if not "floor" in intoName and not "plate" in intoName:
            return
        # setup the projectile interval
        startPos = self.player.getPos()
        self.jumpstartFloater.setPos(self.player, 0, 0.5, 0)
        tempFloater = NodePath(PandaNode("tempJumpFloater"))
        tempFloater.setPos(self.player, 0, -3.2, 0.1)
        endPos = tempFloater.getPos()
        tempFloater.removeNode()
        self.jumpInterval = ProjectileInterval(
            self.player, startPos=startPos, endPos=endPos, duration=1.5, gravityMult=0.25
        )
        self.request("Jump")
        self.jumpInterval.start()

    #
    # CAMERA FUNCTIONS
    #
    def updateCam(self, task):
        if self.mode == Player.NormalMode:
            self.__normalCam()
        else:
            self.__fightCam()
        return task.cont

    def zoom(self, zoomIn):

        # Camera Movement Updates
        camvec = self.player.getPos() - camera.getPos()
        camvec.setZ(0)
        camdist = camvec.length()

        zoom = 0
        if zoomIn:
            if camdist > self.minCamDistance + 0.5:
                zoom = 0.5
            for event in self.camZoomInEvents:
                self.acceptOnce(event, self.zoom, [True])
        else:
            if camdist < self.maxCamDistance - 0.5:
                zoom = -0.5
            for event in self.camZoomOutEvents:
                self.acceptOnce(event, self.zoom, [False])
        camera.setPos(camera, 0, zoom, 0)

    def center(self):
        # Camera Movement Updates
        camvec = self.player.getPos() - camera.getPos()
        camvec.setZ(0)
        camdist = camvec.length()
        # get the cameras current offset to the player model on the z-axis
        offsetZ = camera.getZ() - self.player.getZ()
        camera.setPos(self.player, 0, camdist, offsetZ)
        for event in self.camCenterEvents:
            self.acceptOnce(event, self.center)

    def __normalCam(self):
        """This function will check the min and max distance of the camera to
        the defined model and will correct the position if the cam is to close
        or to far away"""

        # Camera Movement Updates
        camvec = self.player.getPos() - camera.getPos()
        camvec.setZ(0)
        camdist = camvec.length()
        camvec.normalize()

        # If far from player start following
        if camdist > self.maxCamDistance:
            camera.setPos(camera.getPos() + camvec * (camdist - self.maxCamDistance))
            camdist = self.maxCamDistance

        # If player to close move cam backwards
        if camdist < self.minCamDistance:
            camera.setPos(camera.getPos() - camvec * (self.minCamDistance - camdist))
            camdist = self.minCamDistance

        # get the cameras current offset to the player model on the z-axis
        offsetZ = camera.getZ() - self.player.getZ()
        # check if the camera is within the min and max z-axis offset
        if offsetZ < self.minCamHeightDist:
            camera.setZ(self.player.getZ() + self.minCamHeightDist)
            offsetZ = self.minCamHeightDist
        elif offsetZ > self.maxCamHeightDist:
            camera.setZ(self.player.getZ() + self.maxCamHeightDist)
            offsetZ = self.maxCamHeightDist

        if offsetZ != self.camHeightAvg and not base.controlType == Player.MOUSEANDKEYBOARD:
            # if we are not moving up or down, set the cam to an average position
            if offsetZ != self.camHeightAvg:
                if offsetZ > self.camHeightAvg:
                    # the cam is higher then the average cam height above the player
                    # so move it slowly down
                    camera.setZ(camera.getZ() - 5 * globalClock.getDt())
                    newOffsetZ = camera.getZ() - self.player.getZ()
                    # check if the cam has reached the desired offset
                    if newOffsetZ < self.camHeightAvg:
                        # set the cam z position to exactly the desired offset
                        camera.setZ(self.player.getZ() + self.camHeightAvg)
                else:
                    # the cam is lower then the average cam height above the player
                    # so move it slowly up
                    camera.setZ(camera.getZ() + 5 * globalClock.getDt())
                    newOffsetZ = camera.getZ() - self.player.getZ()
                    # check if the cam has reached the desired offset
                    if newOffsetZ > self.camHeightAvg:
                        # set the cam z position to exactly the desired offset
                        camera.setZ(self.player.getZ() + self.camHeightAvg)

        camera.lookAt(self.camFloater)

    def __fightCam(self):
        """This function will check the min and max distance of the camera to
        the defined model and will correct the position if the cam is to close
        or to far away"""
        camera.setX(self.player, 0)
        camera.setY(self.player, self.fightCamDistance)
        camera.setZ(0.5)

        camera.lookAt(self.camFloater)

    #
    # FSM FUNCTIONS
    #
    def enterIdle(self):
        if self.mode == Player.NormalMode:
            self.player.loop("Idle")
            self.footstep.stop()
        elif self.mode == Player.FightMode:
            self.player.loop("Fight_Idle")
            self.footstep.stop()

    def enterRun(self):
        self.player.loop("Run")
        self.footstep.play()

    def enterRunReverse(self):
        self.player.loop("Run")
        self.footstep.play()

    def enterAction(self):
        if self.player.getAnimControl("Hit").isPlaying() or self.player.getAnimControl("Death").isPlaying():
            self.__exitAction()
            return
        self.isActionmove = True
        if self.mode == Player.NormalMode:
            self.__enterActivate()
        elif self.mode == Player.FightMode:
            self.__enterFightAttack()
        self.accept("ActionDone", self.__exitAction)

    def __exitAction(self):
        self.isActionmove = False
        for event in self.actionEvents:
            self.acceptOnce(event, self.request, ["Action"])

    def __enterActivate(self):
        activateAnim = self.player.actorInterval("Activate", playRate=3)
        activateAnim.setDoneEvent("ActionDone")
        activateAnim.start()
        base.messenger.send("Player_Activate")
        self.footstep.stop()

    def enterDeath(self):
        self.footstep.stop()
        deathAnim = self.player.actorInterval("Death")
        deathComplete = None
        if self.health == 0:
            self.deathComplete = Sequence(deathAnim, Wait(2), Func(self.gameOver))
        else:
            self.deathComplete = Sequence(deathAnim, Wait(2), Func(self.resetPlayerPos))
        self.deathComplete.start()

    def enterJump(self):
        self.player.play("Jump")
        self.footstep.stop()

    def enterHit(self):
        self.player.setPlayRate(4, "Hit")
        self.player.play("Hit")
        self.footstep.stop()

    def __enterFightAttack(self):
        attackAnim = self.player.actorInterval("Fight_Attack", playRate=3)
        attackAnim.setDoneEvent("ActionDone")
        attackAnim.start()
        self.spearAttackSfx.play()
        for i in range(self.attackqueue.getNumEntries()):
            entry = self.attackqueue.getEntry(i)
            into = entry.getIntoNode()
            if "golemHitField" in into.getName():
                if random.random() > 0.15:
                    base.messenger.send("HitEnemy")
        self.footstep.stop()

    def enterFightLeft(self):
        self.player.loop("Fight_Left")
        self.footstep.play()

    def enterFightRight(self):
        self.player.loop("Fight_Right")
        self.footstep.play()
예제 #14
0

#** This is a task function called each frame, where the collision ray position is syncronized with the mouse pointer position
def rayupdate(task):
    if base.mouseWatcherNode.hasMouse():
        mpos = base.mouseWatcherNode.getMouse()
        # this function will set our ray to shoot from the actual camera lenses off the 3d scene, passing by the mouse pointer position, making  magically hit what is pointed by it in the 3d space
        pickerRay.setFromLens(base.camNode, mpos.getX(), mpos.getY())
    return task.cont


#** Now the tricky part: we have here a particular kind of pattern that react firing a task event when a collider, tagged as 'rays', whatever the value is stored into, hit an object tagged as 'balls', no matter what value is stored into its tag. The resulting event strings sent to the panda3D event manager will be the result of the FROM collider (ray) and the tag value owned by the INTO object being hit (a ball), provided that was settled with a tag key 'balls'.
# That said, these two lines will catch all the events for either smiles and frowneys because we both tagged 'em as 'balls', for all IN events...
collisionHandler.addInPattern("%(rays)ft-into-%(balls)it")
# ...and here for the OUT events
collisionHandler.addOutPattern("%(rays)ft-out-%(balls)it")

#** To complicate things a little, this time we'll going to use the addAgainPattern method, that will raise an event while the mouse ponter is keeping over a ball of any group. Note that the 'ray_again_all' chunk will be used by the CollisionHandlerEvent to fire the event. See the related accept below.
collisionHandler.addAgainPattern("ray_again_all%("
                                 "rays"
                                 ")fh%("
                                 "balls"
                                 ")ih")
""" Note that we could have been done the same using this form as well:

collisionHandler.addAgainPattern("%(rays)ft-again-%(balls)it")

but then we should have used 2 accepts like this:

DO.accept('ray1-again-smileys', collideAgainBalls)
DO.accept('ray1-again-frowney', collideAgainBalls)
예제 #15
0
class DonkeyKong(ShowBase):
    def __init__(self):
        super().__init__(self)
        self.angle = 0
        self.taskMgr.add(self.setup, "setup")
        self.taskMgr.add(self.update, "update")

        self.scene = self.loader.loadModel('models/DKSet')
        self.scene.reparentTo(self.render)
        
        self.arcadeTexture = self.loader.loadTexture('models/dk-arcade.png')
        self.scene.setTexture(self.arcadeTexture)
        self.scene.setTransparency(1)
        
        self.blocksTexture = self.loader.loadTexture('models/block.png')
        self.stairsTexture = self.loader.loadTexture('models/stairs.png')
        
        self.dkTimer = -1
        self.lifeCounter = 3
        self.playerLost = False
        self.playerWon = False
        #messenger.toggleVerbose()
        
        self.barrels_frames = []
        self.barrels_frames.append(0)
        self.barrels_frames.append( 0.410573 - 0.375774)
        self.barrels_frames.append( 0.444913 - 0.375774)
        self.barrels_frames.append( 0.479941 - 0.375774)
        
    def setup(self,task):
        lens = OrthographicLens()
        lens.setFilmSize(23,19)
        base.camNode.setLens(lens)
        
        self.player = self.scene.attachNewNode("Player")
        
        self.marioGfx = self.scene.find('root/mario')
        self.marioGfx.reparentTo(self.player)
        self.marioGfx.setTwoSided(True)
        
        self.lifes = [
        self.scene.attachNewNode("life1"),
        self.scene.attachNewNode("life2"),
        self.scene.attachNewNode("life3")
        ]
        self.marioGfx.instanceTo(self.lifes[0])
        self.marioGfx.instanceTo(self.lifes[1])
        self.marioGfx.instanceTo(self.lifes[2])
        
        self.lifes[0].setPos(-9,0,7.5)
        self.lifes[1].setPos(-10,0,7.5)
        self.lifes[2].setPos(-11,0,7.5)

        
        self.hammerTime = False
        
        self.hammerDown = self.scene.find('root/hammerdowm')
        self.hammerDown.reparentTo(self.marioGfx)
        self.hammerDown.setPos(1,0,0)
        
        self.hammerUp = self.scene.find('root/hammerup')
        self.hammerUp.reparentTo(self.marioGfx)
        self.hammerUp.setPos(0,0,1)
        
        frame1 = Func(self.hammerFrame1)
        frame2 = Func(self.hammerFrame2)
        delay = Wait(0.1)
        self.hammerSequence = Sequence(frame1, delay, frame2, delay)
        # self.hammerSequence.loop()
        
        self.hammerUp.hide()
        self.hammerDown.hide()
        
        self.scene.find('root/walls').hide()
        self.scene.find('root/rightWall').hide()
        self.scene.find('root/barrel').setPos(0,100,0)
        
        self.jumpAvailable = False
        self.gravity = -.5
        self.verticalTime = 0
        self.v0 = 0
        self.floorZ = 0
        self.onStairs = False
        self.jumpCounter = 1
        # input setup 
        
        self.input = {
        'up':False,
        'down': False,
        'left': False , 
        'right': False,
        'space': False
        }
        
        key_list = ['up','down','left','right']
        for k in key_list:
            self.accept(f'raw-arrow_{k}' , self.buildPress(k) )
            self.accept(f'raw-arrow_{k}-up', self.buildRelease(k) )
        
        self.accept(f'raw-space' , self.buildPress('space') )
        self.accept(f'raw-space-up', self.buildRelease('space') )
        
        
        # collision set up
        base.cTrav = CollisionTraverser()
        self.collisionHandlerEvent = CollisionHandlerEvent()
        self.collisionHandlerEvent.addInPattern('into-%in')
        self.collisionHandlerEvent.addOutPattern('outof-%in')

        ray = CollisionSegment(0,0,0,0,0,-.6)
        cNodePath = self.player.attachNewNode( CollisionNode('marioRay') )
        cNodePath.node().addSolid(ray)
        cNodePath.node().setIntoCollideMask(0x03)
        cNodePath.node().setFromCollideMask(0x03)
        #cNodePath.show()
        base.cTrav.addCollider(cNodePath, self.collisionHandlerEvent)

        self.donkeykong = self.scene.find('root/donkeykong')
        self.donkeykonghit = self.createSquareCollider(8.7,5,1,1,'donkeykong','dkhitbox', 'DK' , self.reachedDK, self.exitDK , self.arcadeTexture, 0x02)
        self.createDkSequence()
        self.dk_sequence.start()
        
        self.floor1 = self.createSquareCollider(-1.8, -5.5 , 9.3, .5, 'floor0' , 'floor1HitBox', 'Floor1', self.enableJump, self.disableJump , self.blocksTexture, 0x1)
        self.floor2 = self.createSquareCollider(2.08, -2.5 , 8.0, .5, 'floor1' , 'floor2HitBox', 'Floor2', self.enableJump, self.disableJump , self.blocksTexture, 0x1)
        self.floor3_1 = self.createSquareCollider(3.6, 0.5 , 3.8, .5, 'floor2' , 'floor3_1HitBox', 'Floor3_1', self.enableJump, self.disableJump , self.blocksTexture, 0x1)
        self.floor3_2 = self.createSquareCollider(-6.3, 0.5 , 5, .5, 'pCube4' , 'floor3_2HitBox', 'Floor3_2', self.enableJump, self.disableJump , self.blocksTexture, 0x1)
        self.floor4 = self.createSquareCollider(1.8, 3.5 , 8.0, .5, 'floors' , 'floor4HitBox', 'Floor4', self.enableJump, self.disableJump , self.blocksTexture, 0x1)
        
        self.hammer = self.createSquareCollider(6,1.5,0.5,0.5,'hammer', 'hammerHitBox', 'hammer', self.enableHammer, self.disableHammer, self.arcadeTexture, 0x02) 
        self.topStair = self.createSquareCollider(-6.8, 3.5 , 0.5, 2.5, 'topstair' , 'topStairHitBox', 'TopStair', self.enableStairs, self.disableStairs , self.stairsTexture, 0x2)
        self.middleStair= self.createSquareCollider(-0.86, 0.1 , 0.5, 2.5, 'middlestair' , 'middleStairHitBox', 'MiddleStair', self.enableStairs, self.disableStairs , self.stairsTexture, 0x2)
        self.bottomStair = self.createSquareCollider(-6.8, -2.5 , 0.5, 2.5, 'bottomstair' , 'bottomStairHitBox', 'BottomStair', self.enableStairs, self.disableStairs , self.stairsTexture, 0x2)
        
        self.leftWall = self.createInvisibleSquareCollider(-12.5, 0, 1, 10 , 'leftWallHitBox','leftWall',0x1)
        self.rightWall = self.createInvisibleSquareCollider(11.3, 0, 1, 20 , 'rightWallHitBox','rightWall',0x1)
        
        self.barrelDestroyer = self.createInvisibleSquareCollider(-.5,-10,10.5,1, 'barrelDestroyerHitBox' , 'barrelDestroyer'  ,0x1) 
        self.barrelBridge = self.createInvisibleSquareCollider(-0.4,0.5,2,0.5, 'barrelBridgeHitBox' , 'barrelBridge'  ,0x4)
        self.accept('into-barrelCollider', self.barrelCrash)
        base.enableParticles()
        
        self.physicsCollisionPusher = PhysicsCollisionHandler()
        gravity = ForceNode('world-forces')
        gravityP = render.attachNewNode(gravity)
        gravityForce = LinearVectorForce(0,0,-9.81)
        gravity.addForce(gravityForce)
        base.physicsMgr.addLinearForce(gravityForce)
        
        
        #self.createInvisibleSquareCollider(0,0,8,3,"NewCollision","NewNode")
        #self.createInvisibleSquareCollider(-6,0,4,5,"NewCollisio2","NewNode2")
        #base.cTrav.showCollisions(self.render)
        
        # self.accept('raw-a', self.throwBarrel)
        # self.player.setPos(3,0,-3.5)
        self.player.setPos(-8,0,-1.5)
        return Task.done

    def reachedDK(self, evt):
        if self.hammerTime:
            self.playerWon = True
        else:
            self.playerLost = True
        pass
    
    def exitDK(self, evt):
        pass

    def calcNextBarrelThrow(self):
        self.dkTimer = random()*3+3

    def changeDkFrame(self, dk,new_u, new_v):
        self.dkTimer = -1
        dk.setTexOffset( TextureStage.getDefault() , new_u , new_v )

    def createDkSequence(self):
        f1 = Func(self.changeDkFrame, self.donkeykong , 0.1408067 - 0.0446603 , 0 )
        f2 = Func(self.changeDkFrame, self.donkeykong , 0.0431023 - 0.0446603 , 0.806672 - 0.703844 )
        f3 = Func(self.changeDkFrame, self.donkeykong , 0 , 0 )
        th = Func(self.throwBarrel)
        reset = Func(self.calcNextBarrelThrow)
        d = Wait(0.2)
        
        self.dk_sequence = Sequence(f1,d,f2,d,f3,th,d,f1,reset)


    def barrelCrash(self, evt):
        physicalBarrel = evt.getIntoNodePath().node().getParent(0).getParent(0)
        other = evt.getFromNodePath().node().getParent(0)
        
    
        if( other.name == 'leftWall' or other.name == 'rightWall'):
            forceNode = physicalBarrel.getChildren()[1]
            force = forceNode.getForce(0)
            force.setVector( force.getLocalVector().x*-1 , 0 ,0 )
            forceNode.clear()
            forceNode.addForce(force)
            
        if( other.name == 'barrelDestroyer' ):
            self.scene.node().removeChild( physicalBarrel.getParent(0) )
        
        
        if( other.name == 'Player' ):
            if(self.hammerTime):
                self.scene.node().removeChild( physicalBarrel.getParent(0) )
            else:
                self.minusLife()
    
    def minusLife(self):
        self.lifes[self.lifeCounter-1].hide()
        self.lifeCounter -= 1
        
        if( self.lifeCounter <= 0):
            self.playerLost = True

    def hammerFrame1(self):
        self.hammerUp.show()
        self.hammerDown.hide()

    
    def hammerFrame2(self):
        self.hammerUp.hide()
        self.hammerDown.show()
    

    def enableHammer(self, evt):
        self.hammerTime = True
        self.scene.node().removeChild( evt.getIntoNodePath().node().getParent(0) )
        self.hammerSequence.loop()
                
    def disableHammer(self, evt):
        pass

    def enableJump(self, evt):
        #print(f'IN----> {evt}')
        self.floorZ = evt.getIntoNodePath().node().getParent(0).getTransform().getPos().z + 1
        self.jumpAvailable = True
    
    def disableJump(self, evt):
        #print(f'Out----> {evt}')
        self.jumpAvailable = False

    def enableStairs(self, evt):
        #print(f'IN----> {evt}')
        self.onStairs = True
    
    def disableStairs(self, evt):
        #print(f'Out----> {evt}')
        self.onStairs = False



    def throwBarrel(self):
        barrelNode = self.scene.attachNewNode("PhysicalBarrel")
        physicalBarrel = ActorNode("physics_barrel")
        physicalBarrel.getPhysicsObject().setMass(0.01)
        
        barrel = barrelNode.attachNewNode(physicalBarrel)
        base.physicsMgr.attachPhysicalNode(physicalBarrel)
        
        visualBarrel = barrel.attachNewNode("BarrelCopy")
        originalBarrel = self.scene.find('root/barrel')
        originalBarrel.instanceTo(visualBarrel)
        visualBarrel.setPos(0,-100,0)
        
        sphere = CollisionSphere(0.16,100,0,0.5)
        cNodePath = visualBarrel.attachNewNode( CollisionNode("barrelCollider") )
        cNodePath.node().addSolid(sphere)
        cNodePath.node().setIntoCollideMask(0x05)
        cNodePath.node().setFromCollideMask(0x05)
        #cNodePath.show()
        
        self.physicsCollisionPusher.addCollider(cNodePath, barrel)
        base.cTrav.addCollider(cNodePath, self.physicsCollisionPusher)
        
        barrelForceNode = ForceNode("barrelForce")
        barrel.attachNewNode(barrelForceNode)
        barrelForce = LinearVectorForce(-8,0,0,1,False)
        barrelForceNode.addForce(barrelForce)
        physicalBarrel.getPhysical(0).addLinearForce(barrelForce)
        
        barrelNode.setPos(self.scene,7 , 0 , 4.5)
        
        dataNode = AuxNode("sequenceData")
        seq = self.createBarrelSequence(visualBarrel , physicalBarrel, dataNode )
        dataNode.setSequence(seq)
        barrelNode.attachNewNode(dataNode)
    
    def createBarrelSequence(self, vBarrel, pBarrel, dNode ):
        
        def updateBarrel():
            vel = pBarrel.getPhysicsObject().getVelocity()
            
            frame = dNode.frame
            
            if( vel.x > 0 ):
                frame = (frame+1)%4
            if( vel.x < 0):
                frame = (frame-1)%4
                
            dNode.frame = frame
            vBarrel.setTexOffset( TextureStage.getDefault() , self.barrels_frames[frame] , 0 )
            
        f1 = Func(updateBarrel)
        d = Wait(0.1)
        
        seq = Sequence(f1,d)
        seq.loop()
        return seq
        
    def createSquareCollider(self, px,pz, w, h, modelName, collisionNodeName, nodeName , intoFunction, outFunction, texture, mask ):
        obj = self.scene.attachNewNode(nodeName)
        hitBox = CollisionBox( Point3(0,0,0), w, 5, h )
        cNodePath = obj.attachNewNode( CollisionNode(collisionNodeName) )
        cNodePath.node().addSolid(hitBox)
        cNodePath.node().setIntoCollideMask(mask)
        cNodePath.node().setFromCollideMask(mask)
        #cNodePath.show()
        base.cTrav.addCollider(cNodePath, self.collisionHandlerEvent)
        
        self.scene.find(f'root/{modelName}').reparentTo(obj)
        obj.setPos(px,0,pz)
        obj.setTexture(texture)
        
        self.accept(f'into-{collisionNodeName}' , intoFunction)
        self.accept(f'outof-{collisionNodeName}' , outFunction)
        
        
        return obj
    

    def createInvisibleSquareCollider(self, px,pz, w, h, collisionNodeName, nodeName , mask ):
        obj = self.scene.attachNewNode(nodeName)
        hitBox = CollisionBox( Point3(0,0,0), w, 5, h )
        cNodePath = obj.attachNewNode( CollisionNode(collisionNodeName) )
        cNodePath.node().addSolid(hitBox)
        cNodePath.node().setIntoCollideMask(mask)
        cNodePath.node().setFromCollideMask(mask)
        #cNodePath.show()
        base.cTrav.addCollider(cNodePath, self.collisionHandlerEvent)
        obj.setPos(px,0,pz)
        
    
    def buildPress(self,key):
        def pressKey():
            self.input[key] = True
        return pressKey
        
    def buildRelease(self, key):
        def releaseKey():
            self.input[key] = False
        return releaseKey

    def applyMove(self):
        
        mv = Vec3(0,0,0)
        p = self.player.getPos()
        
        if( self.input["right"]):
            mv.x = -.1
            self.marioGfx.setSx(self.player , -1)        
            self.lifes[0].setSx(-1)
            self.lifes[1].setSx(-1)
            self.lifes[2].setSx(-1)
                    
            
        if( self.input["left"]):
            mv.x = .1
            self.marioGfx.setSx(self.player , 1)
            self.lifes[0].setSx(1)
            self.lifes[1].setSx(1)
            self.lifes[2].setSx(1)
            
        """
        if( self.input["space"]):
            playerPos.z += .1
            
        if( self.input["down"]):
            playerPos.z -= .1
        """
        
        if( self.jumpAvailable and not self.onStairs ):
            self.jumpCounter = 1
            self.verticalTime = 0
            self.v0 = 0
            p.z = self.floorZ
            if(self.input["space"]):
                self.v0 = .165
                self.jumpAvailable = False
            
        if(not self.jumpAvailable and not self.onStairs):
            self.verticalTime += globalClock.getDt()
            mv.z = self.v0  + self.gravity*self.verticalTime
            
        if( self.onStairs):
            self.jumpCounter = 0
            self.v0 = 0
            if( self.input["down"]):
                mv.z = -.1
            if( self.input["up"]):
                mv.z = .1
            
        if( not self.onStairs ):
            if(not self.jumpAvailable):
                if(self.input["space"] and self.jumpCounter == 0):
                    self.v0 = .165
                    self.jumpAvailable = False
                    self.jumpCounter = 1
            
        p.x += mv.x
        p.z += mv.z
        
        self.player.setPos(p)
        
        # hacer que se pueda agarrar el martillo, cuando suceda : self.marioGfx.setSx(self.player  , -1)
        # self.hammer = self.createSquareCollider(6,1.5,.5,.5,'hammer','hammerHitbox', 'hammer', self.enableHammer, self.disableHammer, self.arcadeTexture, 0x02)
        
        
    def update(self, task):
        self.camera.setPos(0,35,0)
        self.camera.lookAt(self.scene)
        
        if( self.dkTimer > -1):
            self.dkTimer -= globalClock.getDt()
            if(self.dkTimer <= 0):
                self.dk_sequence.start()
        
        if( self.playerLost):
            text = DirectLabel(text="Player Lost" , text_scale=(0.5,0.5) )
            return Task.done
            
        if( self.playerWon):
            text = DirectLabel(text="Player Won" , text_scale=(0.5,0.5) )
            return Task.done
            
                    
        self.applyMove()
            
        return Task.cont  
예제 #16
0
class Player(DirectObject):
    def __init__(self, _main):
        self.main = _main
        self.name = ""
        self.points = 0
        self.health = 100.0
        self.runSpeed = 1.8
        self.keyMap = {
            "left":False,
            "right":False,
            "up":False,
            "down":False
            }
        base.camera.setPos(0,0,0)
        self.model = loader.loadModel("Player")
        self.model.find('**/+SequenceNode').node().stop()
        self.model.find('**/+SequenceNode').node().pose(0)
        base.camera.setP(-90)
        self.playerHud = Hud()
        self.playerHud.hide()
        self.model.hide()

        # Weapons: size=2, 0=main, 1=offhand
        self.mountSlot = []
        self.activeWeapon = None
        self.isAutoActive = False
        self.trigger = False
        self.lastShot = 0.0
        self.fireRate = 0.0

        self.playerTraverser = CollisionTraverser()
        self.playerEH = CollisionHandlerEvent()
        ## INTO PATTERNS
        self.playerEH.addInPattern('intoPlayer-%in')
        #self.playerEH.addInPattern('colIn-%fn')
        self.playerEH.addInPattern('intoHeal-%in')
        self.playerEH.addInPattern('intoWeapon-%in')
        ## OUT PATTERNS
        self.playerEH.addOutPattern('outOfPlayer-%in')
        playerCNode = CollisionNode('playerSphere')
        playerCNode.setFromCollideMask(BitMask32.bit(1))
        playerCNode.setIntoCollideMask(BitMask32.bit(1))
        self.playerSphere = CollisionSphere(0, 0, 0, 0.6)
        playerCNode.addSolid(self.playerSphere)
        self.playerNP = self.model.attachNewNode(playerCNode)
        self.playerTraverser.addCollider(self.playerNP, self.playerEH)
        #self.playerNP.show()

        self.playerPusher = CollisionHandlerPusher()
        self.playerPusher.addCollider(self.playerNP, self.model)
        self.playerPushTraverser = CollisionTraverser()
        self.playerPushTraverser.addCollider(self.playerNP, self.playerPusher)

    def acceptKeys(self):
        self.accept("w", self.setKey, ["up", True])
        self.accept("w-up", self.setKey, ["up", False])
        self.accept("a", self.setKey, ["left", True])
        self.accept("a-up", self.setKey, ["left", False])
        self.accept("s", self.setKey, ["down", True])
        self.accept("s-up", self.setKey, ["down", False])
        self.accept("d", self.setKey, ["right", True])
        self.accept("d-up", self.setKey, ["right", False])

        # Add mouse btn for fire()
        self.accept("mouse1", self.setWeaponTrigger, [True])
        self.accept("mouse1-up", self.setWeaponTrigger, [False])

        # Killed enemies
        self.accept("killEnemy", self.addPoints)

        # Game states
        self.accept("doDamageToPlayer", self.doDamage)

    def ignoreKeys(self):
        self.ignore("w")
        self.ignore("a")
        self.ignore("s")
        self.ignore("d")
        self.ignore("killEnemy")
        self.ignore("mouse1")
        self.ignore("mouse1-up")

        for item in self.main.itemList:
            if item.type == "heal":
                self.ignore("intoHeal-" + "itemHeal" + str(item.id))
            elif item.type == "gun":
                self. ignore("intoWeapon-" + "itemWeapon" + str(item.id))

        for enemy in self.main.enemyList:
            self.ignore("intoPlayer-" + "colEnemy" + str(enemy.id))

        # Add mouse btn for fire to ignore

    def setKey(self, action, pressed):
        self.keyMap[action] = pressed

    def start(self, startPos, playerName):
        self.name = playerName
        self.points = 0
        self.health = 100
        self.model.reparentTo(render)
        self.model.setPos(startPos.x,
                          startPos.y,
                          0)
        for slot in self.mountSlot[:]:
            self.mountSlot.remove(slot)
        # Create a basic weapon
        self.mountSlot.append(Weapon(self.main, "Pistol", 0.30, 25, weaponType="Pistol"))
        # Mount the players default weapon
        self.mountWeapon(self.mountSlot[0])
        self.playerHud.setWeapon("Pistol")

        self.acceptKeys()
        self.playerHud.show()

        taskMgr.add(self.move, "moveTask")

    def stop(self):
        taskMgr.remove("moveTask")
        self.ignoreKeys()
        self.unmountWeapon()
        self.playerHud.hide()
        self.model.hide()

    def addPoints(self, args):
        self.points += 10
        base.messenger.send("setHighscore", [self.points])

    def move(self, task):
        elapsed = globalClock.getDt()
        #self.playerTraverser.traverse(self.main.enemyParent)
        #self.playerTraverser.traverse(self.main.itemParent)

        # set headding
        pos = self.main.mouse.getMousePos()
        pos.setZ(0)
        self.model.lookAt(pos)
        self.model.setP(-90)

        # new player position
        if self.keyMap["up"]:
            # follow mouse mode
            #self.model.setZ(self.model, 5 * elapsed * self.runSpeed)
            # axis move mode
            self.model.setY(self.model.getY() + elapsed * self.runSpeed)
        elif self.keyMap["down"]:
            #self.model.setZ(self.model, -5 * elapsed * self.runSpeed)
            self.model.setY(self.model.getY() - elapsed * self.runSpeed)

        if self.keyMap["left"]:
            # follow mouse mode
            #self.model.setX(self.model, -5 * elapsed * self.runSpeed)
            # axis move mode
            self.model.setX(self.model.getX() - elapsed * self.runSpeed)
        elif self.keyMap["right"]:
            #self.model.setX(self.model, 5 * elapsed * self.runSpeed)
            self.model.setX(self.model.getX() + elapsed * self.runSpeed)

        # actualize cam position
        base.camera.setPos(self.model.getPos())
        base.camera.setZ(20)
        return task.cont

    def mountWeapon(self, _weaponToMount):
        self.activeWeapon = _weaponToMount # self.mountSlot[0]
        if self.activeWeapon.style == "TwoHand":
            self.model.find('**/+SequenceNode').node().pose(0)
        else:
            self.model.find('**/+SequenceNode').node().pose(1)
        self.activeWeapon.model.reparentTo(self.model)
        self.activeWeapon.model.setY(self.model.getY() - 0.1)
        self.model.show()
        self.activeWeapon.model.show()
        self.fireRate = self.activeWeapon.fireRate

    def unmountWeapon(self):
        self.activeWeapon.model.hide()

    def setWeaponTrigger(self, _state):
        self.trigger = _state

        if _state:
            mpos = self.main.mouse.getMousePos()
            self.activeWeapon.doFire(mpos)
            if self.activeWeapon.weaponType == "MG":
                self.fireActiveWeapon()
            else:
                self.activeWeapon.stopFire()
        else:
            self.activeWeapon.stopFire()
            taskMgr.remove("Fire")

    def fireActiveWeapon(self):
        if self.activeWeapon:
            #mpos = self.main.mouse.getMousePos()
            taskMgr.add(self.fireUpdate, "Fire")
            #self.activeWeapon.doFire(mpos)

    def fireUpdate(self, task):
        dt = globalClock.getDt()
        self.lastShot += dt
        mpos = self.main.mouse.getMousePos()
        #print self.lastShot
        if self.lastShot >= self.fireRate:
            self.lastShot -= self.fireRate

            if self.trigger:
                self.activeWeapon.doFire(mpos)
                #task.delayTime += self.fireRate
        return task.again

    def setMouseBtn(self):
        self.trigger = False

        print "Mouse Released"

    def addEnemyDmgEvent(self, _id):
        self.accept("intoPlayer-" + "colEnemy" + str(_id), self.setEnemyAttack)
        #self.accept("outOfPlayer-" + "colEnemy" + str(_id), self.setEnemyAttackOutOfRange)

    def setEnemyAttack(self, _entry):
        enemyColName = _entry.getIntoNodePath().node().getName()
        base.messenger.send("inRange-" + enemyColName, [True])

    def setEnemyAttackOutOfRange(self, _entry):
        enemyColName = _entry.getIntoNodePath().node().getName()
        base.messenger.send("inRange-" + enemyColName, [False])

    def doDamage(self, _dmg):

        if self.health <= 0:
            #print "KILLED IN ACTION"
            self.main.stop()
        else:
            self.health -= _dmg
            #print "Remaining Health: ", self.health
        base.messenger.send("setHealth", [self.health])

    def addHealItemEvent(self, _id):
        self.accept("intoHeal-" + "itemHeal" + str(_id), self.healPlayer)

    def healPlayer(self, _entry):
        itemColName = _entry.getIntoNodePath().node().getName()

        if self.health == 100:
            pass

        else:
            self.health += 50
            base.messenger.send("into-" + itemColName)
            if self.health > 100:
                self.health = 100

        print self.health

    def addWeaponItemEvent(self, _id):
        self.accept("intoWeapon-" + "itemWeapon" + str(_id), self.changeWeapon)

    def changeWeapon(self, _entry):
        itemColName = _entry.getIntoNodePath().node().getName()
        base.messenger.send("into-" + itemColName)
        for weapon in self.mountSlot:
            if weapon.name == "MachineGun":
                return
        self.unmountWeapon()
        self.mountSlot.append(Weapon(self.main, "MachineGun", 0.15, 50, weaponType="MG"))
        self.playerHud.setWeapon("MG")
        self.mountWeapon(self.mountSlot[len(self.mountSlot) - 1])
        self.activeWeapon.model.show()
class Starfox(ShowBase):
    def __init__(self):
        self.height = 500
        super().__init__(self)
        self.scene = self.loader.loadModel("./models/world.egg")
        playerTexture = loader.loadTexture("models/starfoxShip.jpg")
        enemyTexture = loader.loadTexture("models/enemyShip.jpg")
        bulletTexture = loader.loadTexture("models/shot.png")
        self.scene.reparentTo(self.render)

        base.setBackgroundColor(0.1, 0.1, 0.1, 1)

        self.player = self.scene.find("player")
        self.player.setPythonTag("ObjectController", Player(self.player))
        self.player.setTexture(playerTexture)

        self.building_enemy = self.scene.find("building_enemy")
        self.dynamic_enemy = self.scene.find("enemy1")
        self.dynamic_enemy.setTexture(enemyTexture)
        self.bullet = self.scene.find("bullet")
        self.bullet.setTexture(bulletTexture)

        base.cTrav = CollisionTraverser()
        self.CollisionHandlerEvent = CollisionHandlerEvent()
        base.enableParticles()
        self.CollisionHandlerEvent.addInPattern('into-%in')
        self.CollisionHandlerEvent.addOutPattern('out-%in')

        self.accept('into-collision_player', self.crash)
        self.accept('into-collision_plane', self.crash)
        self.accept('into-collision_enemy', self.crash)

        base.cTrav.addCollider(self.scene.find("player/collision**"),
                               self.CollisionHandlerEvent)
        base.cTrav.addCollider(self.scene.find("basePlane/collision**"),
                               self.CollisionHandlerEvent)

        self.player.find("**collision**").node().setFromCollideMask(0x3)
        self.player.find("**collision**").node().setIntoCollideMask(0x3)

        self.dynamic_enemy.find("**collision**").node().setFromCollideMask(0x5)
        self.dynamic_enemy.find("**collision**").node().setIntoCollideMask(0x5)

        self.building_enemy.find("**collision**").node().setFromCollideMask(
            0x5)
        self.building_enemy.find("**collision**").node().setIntoCollideMask(
            0x5)

        #base.cTrav.showCollisions(self.render)

        self.taskMgr.add(self.update, "update")
        InputManager.initWith(self, [
            InputManager.arrowUp, InputManager.arrowDown,
            InputManager.arrowLeft, InputManager.arrowRight,
            InputManager.space, InputManager.keyX, InputManager.keyV
        ])

        self.rails = self.scene.attachNewNode("rails")
        self.scene.find("basePlane").setHpr(70, 0, 0)
        self.rails.setPos(self.scene, 0, 0, 0)
        self.player.reparentTo(self.rails)
        self.player.setPos(self.rails, 0, 0, 0)
        self.rails_y = -50

        self.createStaticEnemy(self.building_enemy, 0, 50, 0)
        self.createStaticEnemy(self.building_enemy, -50, 50, 0)
        self.createStaticEnemy(self.building_enemy, -100, 50, 0)
        self.createStaticEnemy(self.building_enemy, -70, 130, 0)
        self.createStaticEnemy(self.building_enemy, -120, 80, 0)
        self.createStaticEnemy(self.building_enemy, -220, 130, 0)

        DynamicEnemy(self.dynamic_enemy,
                     self.scene,
                     Vec3(-230, 140, 10),
                     base.cTrav,
                     self.CollisionHandlerEvent,
                     type=ENEMY_TYPE.CHASER)
        #DynamicEnemy(self.dynamic_enemy, self.scene, Vec3(-240,160,10) ,  base.cTrav, self.CollisionHandlerEvent)
        #DynamicEnemy(self.dynamic_enemy, self.scene, Vec3(-250,200,10) ,  base.cTrav, self.CollisionHandlerEvent)
        #DynamicEnemy(self.dynamic_enemy, self.scene, Vec3(-270,160,10) ,  base.cTrav, self.CollisionHandlerEvent)
        #DynamicEnemy(self.dynamic_enemy, self.scene, Vec3(-250,200,10) ,  base.cTrav, self.CollisionHandlerEvent)

        self.building_enemy.hide()
        self.dynamic_enemy.hide()

        self.fog = Fog("fog")
        self.fog.setColor(0.1, 0.1, 0.1)
        self.fog.setExpDensity(.3)
        self.fog.setLinearRange(50, 150)
        self.fog.setLinearFallback(45, 160, 320)
        self.render.setFog(self.fog)

        self.dirLight = DirectionalLight("dir light")
        self.dirLight.color = (0.7, 0.7, 1, 1)
        self.dirLightPath = self.render.attachNewNode(self.dirLight)
        self.dirLightPath.setHpr(45, -45, 0)
        self.dirLight.setShadowCaster(True, 512, 512)
        render.setLight(self.dirLightPath)

        filters = CommonFilters(base.win, base.cam)
        filters.setBloom(size="large", mintrigger=0.2)

        self.render.setShaderAuto()

        self.initSounds()
        self.initUI()
        self.onGame = False

    def initUI(self):
        self.font = loader.loadFont('./fonts/Magenta.ttf')

        self.lifes = [
            OnscreenImage(image='./UI/fox-icon-png-8.png',
                          pos=(1.1, 0, 0.8),
                          scale=0.05),
            OnscreenImage(image='./UI/fox-icon-png-8.png',
                          pos=(1.2, 0, 0.8),
                          scale=0.05)
        ]

        self.lifes[0].setTransparency(True)
        self.lifes[1].setTransparency(True)

        self.dialogScreen = DirectDialog(frameSize=(-0.7, 0.7, -0.7, 0.7),
                                         relief=DGG.FLAT)

        s = OnscreenImage(image='./UI/fox-icon-png-8.png',
                          pos=(0, 0, -0.2),
                          scale=0.20,
                          parent=self.dialogScreen)
        s.setTransparency(True)

        self.titleUI = DirectLabel(text="Starfox Region 4",
                                   parent=self.dialogScreen,
                                   scale=0.1,
                                   pos=(0, 0, .2),
                                   text_font=self.font)

        self.btn = DirectButton(text="Start",
                                command=self.startGame,
                                pos=(0, 0, 0),
                                parent=self.dialogScreen,
                                scale=0.07)

    def startGame(self):
        self.dialogScreen.hide()
        self.flyingSound.play()
        self.onGame = True
        self.btn.hide()

    def initSounds(self):
        self.audio3d = Audio3DManager.Audio3DManager(base.sfxManagerList[0],
                                                     self.camera)

        self.flyingSound = self.audio3d.loadSfx(
            "./sounds/great fox flying.mp3")
        self.flyingSound.setLoop(True)

        self.audio3d.attachSoundToObject(self.flyingSound, self.player)
        self.audio3d.setSoundVelocityAuto(self.flyingSound)
        self.audio3d.setListenerVelocityAuto()
        #self.audio3d.setDistanceFactor(100)
        self.audio3d.setDropOffFactor(0)

        self.fireSound = self.audio3d.loadSfx(
            "./sounds/arwing double laser one shot.mp3")
        self.crashSound = self.audio3d.loadSfx("./sounds/break.mp3")

    def createStaticEnemy(self, original, px, py, pz):
        be = original.copyTo(self.scene)
        be.setPos(px, py, pz)
        base.cTrav.addCollider(be.find("**collision**"),
                               self.CollisionHandlerEvent)
        """
        self.pointLight = PointLight("point light")
        self.pointLight.color = (1,1,1,1)
        self.pointLightPath = self.render.attachNewNode(self.pointLight)
        self.pointLightPath.setPos(px,py,pz)
        self.pointLight.attenuation = (1,0,0)
        #self.pointLight.setShadowCaster(True,1024,1024)
        self.render.setLight(self.pointLightPath)
        """

    def crash(self, evt):

        self.crashSound.play()
        objectInto = evt.getIntoNodePath().node().getParent(0).getPythonTag(
            "ObjectController")
        objectFrom = evt.getFromNodePath().node().getParent(0).getPythonTag(
            "ObjectController")

        if (objectInto != None):
            objectInto.crash(objectFrom)

        if (objectFrom != None):
            objectFrom.crash(objectInto)

        lifes = self.player.getPythonTag("ObjectController").getLifes()
        if (lifes <= 0):
            self.onGame = False
            self.dialogScreen.show()
            self.flyingSound.stop()

    def update(self, evt):
        #self.camera.setPos(0,-100,100)

        lifes = self.player.getPythonTag("ObjectController").getLifes()

        if (lifes > 2):
            self.lifes[0].show()
            self.lifes[1].show()
        elif (lifes > 1):
            self.lifes[0].show()
            self.lifes[1].hide()
        elif (lifes > 0):
            self.lifes[0].hide()
            self.lifes[1].hide()

        self.camera.lookAt(self.player)
        self.rails.setPos(self.scene, Path.getXOfY(self.rails_y), self.rails_y,
                          12.4)
        self.rails.setHpr(Path.getHeading(self.rails_y), 0, 0)
        self.dirLight.color = (self.rails_y / 600, 0.7, 1, 1)
        self.camera.setHpr(Path.getHeading(self.rails_y), 0, 0)

        if (self.onGame):
            self.rails_y = self.rails_y + globalClock.getDt() * 10
            #self.player.setPos(self.rails, 0, 0, sin(self.z/10.0)*40 )
            relX, relZ, isShooting = self.player.getPythonTag(
                "ObjectController").update(self.rails, globalClock.getDt())
            self.camera.setPos(self.rails, relX, -30, relZ)
            if (isShooting):
                self.fireSound.play()
                b = Bullet(
                    self.bullet, self.scene, self.player.getPos(self.scene),
                    base.cTrav, self.CollisionHandlerEvent,
                    self.scene.getRelativeVector(self.player,
                                                 Vec3(0, 1, 0)), 40, 0x4)
            enemies = self.scene.findAllMatches("dynamicEnemy")
            for e in enemies:
                enemy = e.getPythonTag("ObjectController")
                enemy.update(self.scene, globalClock.getDt(), self.player,
                             self.bullet)

            bullets = self.scene.findAllMatches("bulletC")
            for b in bullets:
                bullet = b.getPythonTag("ObjectController")
                bullet.update(self.scene, globalClock.getDt(), self.player)

        return Task.cont
예제 #18
0
class World(DirectObject):
    def __init__(self):
        # Initialize the traverser.
        base.cTrav = CollisionTraverser()

        # Initialize the handler.
        self.collHandEvent = CollisionHandlerEvent()
        self.collHandEvent.addInPattern('into-%in')
        self.collHandEvent.addOutPattern('outof-%in')

        # Make a variable to store the unique collision string count.
        self.collCount = 0

        # Load a model. Reparent it to the camera so we can move it.
        s = base.loader.loadModel('smiley')
        s.reparentTo(base.camera)
        s.setPos(0, 25, 0)

        # Setup a collision solid for this model.
        sColl = self.initCollisionSphere(s, True)

        # Add this object to the traverser.
        base.cTrav.addCollider(sColl[0], self.collHandEvent)

        # Accept the events sent by the collisions.
        self.accept('into-' + sColl[1], self.collide3)
        self.accept('outof-' + sColl[1], self.collide4)
        print(sColl[1])

        # Load another model.
        t = base.loader.loadModel('smiley')
        t.reparentTo(base.render)
        t.setPos(5, 25, 0)

        # Setup a collision solid for this model.
        tColl = self.initCollisionSphere(t, True)

        # Add this object to the traverser.
        base.cTrav.addCollider(tColl[0], self.collHandEvent)

        # Accept the events sent by the collisions.
        self.accept('into-' + tColl[1], self.collide)
        self.accept('outof-' + tColl[1], self.collide2)
        print(tColl[1])

        print("WERT")

    def collide(self, collEntry):
        print("WERT: object has collided into another object")
        collParent = collEntry.getFromNodePath().getParent()
        Sequence(
            Func(collParent.setColor, (1, 0, 0, 1)),
            Wait(0.2),
            Func(collParent.setColor, (0, 1, 0, 1)),
            Wait(0.2),
            Func(collParent.setColor, (1, 1, 1, 1)),
        ).start()

    def collide2(self, collEntry):
        print("WERT.: object is no longer colliding with another object")

    def collide3(self, collEntry):
        print("WERT2: object has collided into another object")

    def collide4(self, collEntry):
        print("WERT2: object is no longer colliding with another object")

    def initCollisionSphere(self, obj, show=False):
        # Get the size of the object for the collision sphere.
        bounds = obj.getChild(0).getBounds()
        center = bounds.getCenter()
        radius = bounds.getRadius() * 1.1

        # Create a collision sphere and name it something understandable.
        collSphereStr = 'CollisionHull{0}_{1}'.format(self.collCount, obj.name)
        self.collCount += 1
        cNode = CollisionNode(collSphereStr)
        cNode.addSolid(CollisionSphere(center, radius))

        cNodepath = obj.attachNewNode(cNode)
        if show:
            cNodepath.show()

        # Return a tuple with the collision node and its corrsponding string so
        # that the bitmask can be set.
        return (cNodepath, collSphereStr)
예제 #19
0
class CogdoFlyingCollisions(GravityWalker):
    wantFloorSphere = 0

    def __init__(self):
        GravityWalker.__init__(self, gravity=0.0)

    def initializeCollisions(self, collisionTraverser, avatarNodePath, avatarRadius = 1.4, floorOffset = 1.0, reach = 1.0):
        self.cHeadSphereNodePath = None
        self.cFloorEventSphereNodePath = None
        self.setupHeadSphere(avatarNodePath)
        self.setupFloorEventSphere(avatarNodePath, ToontownGlobals.FloorEventBitmask, avatarRadius)
        GravityWalker.initializeCollisions(self, collisionTraverser, avatarNodePath, avatarRadius, floorOffset, reach)
        return

    def setupWallSphere(self, bitmask, avatarRadius):
        self.avatarRadius = avatarRadius
        cSphere = CollisionSphere(0.0, 0.0, self.avatarRadius + 0.75, self.avatarRadius)
        cSphereNode = CollisionNode('Flyer.cWallSphereNode')
        cSphereNode.addSolid(cSphere)
        cSphereNodePath = self.avatarNodePath.attachNewNode(cSphereNode)
        cSphereNode.setFromCollideMask(bitmask)
        cSphereNode.setIntoCollideMask(BitMask32.allOff())
        if config.GetBool('want-fluid-pusher', 0):
            self.pusher = CollisionHandlerFluidPusher()
        else:
            self.pusher = CollisionHandlerPusher()
        self.pusher.addCollider(cSphereNodePath, self.avatarNodePath)
        self.cWallSphereNodePath = cSphereNodePath

    def setupEventSphere(self, bitmask, avatarRadius):
        self.avatarRadius = avatarRadius
        cSphere = CollisionSphere(0.0, 0.0, self.avatarRadius + 0.75, self.avatarRadius * 1.04)
        cSphere.setTangible(0)
        cSphereNode = CollisionNode('Flyer.cEventSphereNode')
        cSphereNode.addSolid(cSphere)
        cSphereNodePath = self.avatarNodePath.attachNewNode(cSphereNode)
        cSphereNode.setFromCollideMask(bitmask)
        cSphereNode.setIntoCollideMask(BitMask32.allOff())
        self.event = CollisionHandlerEvent()
        self.event.addInPattern('enter%in')
        self.event.addOutPattern('exit%in')
        self.cEventSphereNodePath = cSphereNodePath

    def setupRay(self, bitmask, floorOffset, reach):
        cRay = CollisionRay(0.0, 0.0, 3.0, 0.0, 0.0, -1.0)
        cRayNode = CollisionNode('Flyer.cRayNode')
        cRayNode.addSolid(cRay)
        self.cRayNodePath = self.avatarNodePath.attachNewNode(cRayNode)
        cRayNode.setFromCollideMask(bitmask)
        cRayNode.setIntoCollideMask(BitMask32.allOff())
        self.lifter = CollisionHandlerGravity()
        self.lifter.setLegacyMode(self._legacyLifter)
        self.lifter.setGravity(self.getGravity(0))
        self.lifter.addInPattern('%fn-enter-%in')
        self.lifter.addAgainPattern('%fn-again-%in')
        self.lifter.addOutPattern('%fn-exit-%in')
        self.lifter.setOffset(floorOffset)
        self.lifter.setReach(reach)
        self.lifter.addCollider(self.cRayNodePath, self.avatarNodePath)

    def setupHeadSphere(self, avatarNodePath):
        collSphere = CollisionSphere(0, 0, 0, 1)
        collSphere.setTangible(1)
        collNode = CollisionNode('Flyer.cHeadCollSphere')
        collNode.setFromCollideMask(ToontownGlobals.CeilingBitmask)
        collNode.setIntoCollideMask(BitMask32.allOff())
        collNode.addSolid(collSphere)
        self.cHeadSphereNodePath = avatarNodePath.attachNewNode(collNode)
        self.cHeadSphereNodePath.setZ(base.localAvatar.getHeight() + 1.0)
        self.headCollisionEvent = CollisionHandlerEvent()
        self.headCollisionEvent.addInPattern('%fn-enter-%in')
        self.headCollisionEvent.addOutPattern('%fn-exit-%in')
        base.cTrav.addCollider(self.cHeadSphereNodePath, self.headCollisionEvent)

    def setupFloorEventSphere(self, avatarNodePath, bitmask, avatarRadius):
        cSphere = CollisionSphere(0.0, 0.0, 0.0, 0.75)
        cSphereNode = CollisionNode('Flyer.cFloorEventSphere')
        cSphereNode.addSolid(cSphere)
        cSphereNodePath = avatarNodePath.attachNewNode(cSphereNode)
        cSphereNode.setFromCollideMask(bitmask)
        cSphereNode.setIntoCollideMask(BitMask32.allOff())
        self.floorCollisionEvent = CollisionHandlerEvent()
        self.floorCollisionEvent.addInPattern('%fn-enter-%in')
        self.floorCollisionEvent.addAgainPattern('%fn-again-%in')
        self.floorCollisionEvent.addOutPattern('%fn-exit-%in')
        base.cTrav.addCollider(cSphereNodePath, self.floorCollisionEvent)
        self.cFloorEventSphereNodePath = cSphereNodePath

    def deleteCollisions(self):
        GravityWalker.deleteCollisions(self)
        if self.cHeadSphereNodePath != None:
            base.cTrav.removeCollider(self.cHeadSphereNodePath)
            self.cHeadSphereNodePath.detachNode()
            self.cHeadSphereNodePath = None
            self.headCollisionsEvent = None
        if self.cFloorEventSphereNodePath != None:
            base.cTrav.removeCollider(self.cFloorEventSphereNodePath)
            self.cFloorEventSphereNodePath.detachNode()
            self.cFloorEventSphereNodePath = None
            self.floorCollisionEvent = None
        self.cRayNodePath.detachNode()
        del self.cRayNodePath
        self.cEventSphereNodePath.detachNode()
        del self.cEventSphereNodePath
        return

    def setCollisionsActive(self, active = 1):
        if self.collisionsActive != active:
            if self.cHeadSphereNodePath != None:
                base.cTrav.removeCollider(self.cHeadSphereNodePath)
                if active:
                    base.cTrav.addCollider(self.cHeadSphereNodePath, self.headCollisionEvent)
            if self.cFloorEventSphereNodePath != None:
                base.cTrav.removeCollider(self.cFloorEventSphereNodePath)
                if active:
                    base.cTrav.addCollider(self.cFloorEventSphereNodePath, self.floorCollisionEvent)
        GravityWalker.setCollisionsActive(self, active)
        return

    def enableAvatarControls(self):
        pass

    def disableAvatarControls(self):
        pass

    def handleAvatarControls(self, task):
        pass
예제 #20
0
    def __init__(self):
	global collide
        ShowBase.__init__(self)

	self.traverser = CollisionTraverser('traverser1')
	base.cTrav = self.traverser
	#traverser.addCollider(cnode1, handler)

	entry = 1

	imageObject = OnscreenImage(image = '/Users/devanshi/Downloads/sky.png', pos = (0, 0, 0), scale = 2)
	imageObject.setTransparency(TransparencyAttrib.MAlpha)
	base.cam.node().getDisplayRegion(0).setSort(20)
		
	self.forest=NodePath(PandaNode("Forest Root"))
        self.forest.reparentTo(render)
        loader.loadModel("models/background").reparentTo(self.forest)
        loader.loadModel("models/foliage01").reparentTo(self.forest)
        loader.loadModel("models/foliage02").reparentTo(self.forest)
        loader.loadModel("models/foliage03").reparentTo(self.forest)
        loader.loadModel("models/foliage04").reparentTo(self.forest)
        loader.loadModel("models/foliage05").reparentTo(self.forest)
        loader.loadModel("models/foliage06").reparentTo(self.forest)
        loader.loadModel("models/foliage07").reparentTo(self.forest)
        loader.loadModel("models/foliage08").reparentTo(self.forest)
        loader.loadModel("models/foliage09").reparentTo(self.forest)
	
	
	self.forest1=NodePath(PandaNode("Forest Root"))
        self.forest1.reparentTo(render)
        
        loader.loadModel("models/foliage01").reparentTo(self.forest1)
        loader.loadModel("models/foliage02").reparentTo(self.forest1)
        loader.loadModel("models/foliage03").reparentTo(self.forest1)
        loader.loadModel("models/foliage04").reparentTo(self.forest1)
        loader.loadModel("models/foliage05").reparentTo(self.forest1)
        loader.loadModel("models/foliage06").reparentTo(self.forest1)
        loader.loadModel("models/foliage07").reparentTo(self.forest1)
        loader.loadModel("models/foliage08").reparentTo(self.forest1)
        loader.loadModel("models/foliage09").reparentTo(self.forest1)

        self.forest.hide(BitMask32.bit(1))
	
        self.forest.setScale(2.5, 2.5, 2.5)
        self.forest.setPos(0, 0, -2)

        self.forest1.hide(BitMask32.bit(1))
	
        self.forest1.setScale(1.5, 1.5, 1.5)
        self.forest1.setPos(-1,-1, 0)

	self.forest2=NodePath(PandaNode("Forest Root"))
        self.forest2.reparentTo(render)
        
        loader.loadModel("models/foliage01").reparentTo(self.forest2)
        loader.loadModel("models/foliage02").reparentTo(self.forest2)
        loader.loadModel("models/foliage03").reparentTo(self.forest2)
        loader.loadModel("models/foliage04").reparentTo(self.forest2)
        loader.loadModel("models/foliage05").reparentTo(self.forest2)
        loader.loadModel("models/foliage06").reparentTo(self.forest2)
        loader.loadModel("models/foliage07").reparentTo(self.forest2)
        loader.loadModel("models/foliage08").reparentTo(self.forest2)
        loader.loadModel("models/foliage09").reparentTo(self.forest2)

        self.forest2.hide(BitMask32.bit(1))

        self.forest1.setScale(1.5, 1.5, 1.5)
        self.forest1.setPos(1,1, 0)

	self.stall = self.loader.loadModel("models/patch/cornfield")
	self.stall.reparentTo(self.render)
	self.stall.setScale(0.5)
	self.stall.setPos(40,0,1)
	self.stall.setHpr(0,0,0)
	self.tex1=self.loader.loadTexture("models/water.png")
	self.stall.setTexture(self.tex1,1)

	self.flock = Actor("models/goose/goosemodelonly",  {"gfly":"models/goose/gooseanimationonly"
                       })

        self.flock.setScale(0.05, 0.05, 0.05)
	self.flock.setPos(0,-30,13)
        self.flock.reparentTo(self.render)
	self.flock.loop("gfly")
	self.tex2=self.loader.loadTexture("models/orange.jpg")
	self.flock.setTexture(self.tex2,1)

	self.camera.setPos(0,0,0)
	self.camera.setHpr(90,0,0)

       # Create the four lerp intervals needed for the panda to
        # walk back and forth.
        pandaPosInterval1 = self.flock.posInterval(13,
                                                        Point3(-5, -30, 13),
                                                        startPos=Point3(5, -30, 13))
        pandaPosInterval2 = self.flock.posInterval(13,
                                                        Point3(5, -30, 13),
                                                        startPos=Point3(-5, -30, 13))
        pandaHprInterval1 = self.flock.hprInterval(3,
                                                        Point3(0, 0, 0),
                                                        startHpr=Point3(180, 0, 0))
        pandaHprInterval2 = self.flock.hprInterval(3,
                                                        Point3(180, 0, 0),
                                                        startHpr=Point3(0, 0, 0))
 
        # Create and play the sequence that coordinates the intervals.
        self.pandaPace = Sequence(pandaPosInterval1,
                                  pandaHprInterval1,
                                  pandaPosInterval2,
                                  pandaHprInterval2,
                                  name="pandaPace")
        self.pandaPace.loop()

		
	
	
        # Disable the camera trackball controls.
        #self.disableMouse()
 
        # Load the environment model.
        self.environ = self.loader.loadModel("models/environment1")
        # Reparent the model to render.
        self.environ.reparentTo(self.render)
        # Apply scale and position transforms on the model.
        self.environ.setScale(0.25, 0.25, 0.25)
        self.environ.setPos(-8, 42, 0)

	self.boy =  Actor("models/trex/trex",  {"run":"models/trex/trex-run",
                                  "eat":"models/trex/trex-eat"})
	self.boy.reparentTo(self.render)
	self.boy.setPos(0,0,0)
	self.boy.setScale(0.5)
	self.isMoving = False
	self.myAnimControl = self.boy.getAnimControl('run')
				
	base.camera.setPos(self.boy.getX(),self.boy.getY()+10,20)
	self.floater = NodePath(PandaNode("floater"))
	self.floater.reparentTo(render)
		
	self.cBoy = self.boy.attachNewNode(CollisionNode('cBoyNode'))
	self.cBoy.node().addSolid(CollisionSphere(0, 0, 3, 8.5))
	#self.cBoy.show()
		
	#self.cPond = self.stall.attachNewNode(CollisionNode('cPond'))
	#self.cPond.node().addSolid(CollisionSphere(40, 0, 1, 70))
	#self.cPond.show()
	
 
        # Add the spinCameraTask procedure to the task manager.
        #self.taskMgr.add(self.spinCameraTask,"asdsad")
	self.keyMap = {"left":0, "right":0, "forward":0, "cam-left":0, "cam-right":0}

	cs1 = CollisionSphere(0, 0, 0, 2)
	self.cnodePath1 = render.attachNewNode(CollisionNode('cnode1'))
	self.cnodePath1.node().addSolid(cs1)
	#self.cnodePath1.setCollideMask(BitMask32(0x10))
	#self.cnodePath1.show()

	
	self.taskMgr.add(self.moveSphere1, "sfasdasf")
 

	cs2 = CollisionSphere(0, 0, 0, 1)
	self.cnodePath2 = render.attachNewNode(CollisionNode('cnode2'))
	self.cnodePath2.node().addSolid(cs2)
	#self.cnodePath2.reparentTo(self.render)
	#self.cnodePath2.node().setFromCollideMask(BitMask32.bit(0))
        #self.cnodePath2.node().setIntoCollideMask(BitMask32.allOff())
	#self.cnodePath2.show()

	self.taskMgr.add(self.moveSphere2, "sfasd")


	handler = CollisionHandlerEvent()
	handler.addInPattern('cnode1-into-cnode2')
	handler.addAgainPattern('cnode1-again-cnode2')
	handler.addOutPattern('cs1-out-cs2')


	self.accept('cnode1-into-cnode2', self.collide)
	#self.accept('cs1-out-cs2', self.collide)
	#self.accept('cnode1-again-cnode2', self.collide)


	self.traverser.addCollider(self.cnodePath1, handler)

        # Load and transform the panda actor.
        self.pandaActor = Actor("models/panda-model",
                                {"walk": "models/panda-walk4"})
        self.pandaActor.setScale(0.005, 0.005, 0.005)
        self.pandaActor.reparentTo(self.render)
        # Loop its animation.
        self.pandaActor.loop("walk")

	self.taskMgr.add(self.movePanda, "Sasdas")
	
	self.pandaActor2 = Actor("models/panda-model",{"walk": "models/panda-walk4"})
        self.pandaActor2.setScale(0.003, 0.003, 0.003)
        self.pandaActor2.reparentTo(self.render)
        # Loop its animation.
        self.pandaActor2.loop("walk")

	self.taskMgr.add(self.movePanda2, "Sak")

	self.camera.setPos(0,0,0)
	self.camera.setHpr(90,0,0)

	self.cTrav1=CollisionTraverser()
	self.collisionHandler1 = CollisionHandlerQueue()
	self.cTrav1.addCollider(self.cBoy, self.collisionHandler1)

	self.taskMgr.add(self.boyMoveTask, "BoyMoveTask")
		
	#self.accept("v",self.switchView)
	self.accept("escape", sys.exit)
	self.accept("arrow_left", self.setKey, ["left",1])
	self.accept("arrow_right", self.setKey, ["right",1])
	self.accept("arrow_up", self.setKey, ["forward",1])
	#self.accept("a", self.setKey, ["cam-left",1])
	#self.accept("s", self.setKey, ["cam-right",1])
	self.accept("arrow_left-up", self.setKey, ["left",0])
	self.accept("arrow_right-up", self.setKey, ["right",0])
	self.accept("arrow_up-up", self.setKey, ["forward",0])
	#self.accept("a-up", self.setKey, ["cam-left",0])
	#self.accept("s-up", self.setKey, ["cam-right",0])

	self.cTrav2=CollisionTraverser()
	self.collisionHandler2 = CollisionHandlerQueue()
예제 #21
0
class DKGame(ShowBase):
    def __init__(self):
        super().__init__(self)
        self.loadScenery()
        self.mario = None
        #base.messenger.toggleVerbose()
        self.taskMgr.add(self.setup, "setup")
        self.taskMgr.add(self.update, "update")

        self.accept("raw-arrow_right", self.pressRight)
        self.accept("raw-arrow_right-up", self.stopRight)
        self.accept("raw-arrow_left", self.pressLeft)
        self.accept("raw-arrow_left-up", self.stopLeft)

        self.accept("raw-arrow_up", self.pressUp)
        self.accept("raw-arrow_up-up", self.stopUp)

        self.accept("raw-space", self.pressSpace)
        self.accept("raw-space-up", self.stopSpace)

        self.canClimb = False
        self.isClimbing = False
        #NUEVA!
        self.isGrounded = True
        self.canJump = True
        self.jumpTime = 0
        self.vyi = 0
        self.floorValidPosition = 0

        self.barrelTimer = 0
        self.lifes = 3

        self.marioInitialPos = None
        self.posNotInitialized = True
        self.hammer = False

        self.input = {
            "left": False,
            "right": False,
            "space": False,
            "up": False
        }

    def loadScenery(self):
        self.scene = self.loader.loadModel(
            "models/DKSet1")  # only for non animated objects
        self.scene.reparentTo(self.render)

    def setup(self, task):
        lens = OrthographicLens()
        lens.setFilmSize(25, 20)  # Or whatever is appropriate for your scene
        base.camNode.setLens(lens)

        node = self.scene.find("root/camera1")
        node.removeNode()
        self.camera.setPos(0, 30, 0)
        self.camera.lookAt(self.scene)

        self.mario = self.scene.find("root/mario")
        self.mario.reparentTo(self.scene)

        self.scene.find("root/bottomstair").reparentTo(self.scene)
        self.scene.find("root/floor0").reparentTo(self.scene)
        self.scene.find("root/floor1").reparentTo(self.scene)

        self.scene.find("root/middlestair").reparentTo(self.scene)
        self.scene.find("root/topstair").reparentTo(self.scene)

        self.scene.find("root/floor2").reparentTo(self.scene)
        self.scene.find("root/pCube4").reparentTo(self.scene)
        self.scene.find("root/floors").reparentTo(self.scene)
        self.scene.find("root/barrel").reparentTo(self.scene)

        self.scene.find("root/walls").reparentTo(self.scene)
        self.scene.find("root/rightWall").reparentTo(self.scene)

        self.scene.find("root/MainGroup").reparentTo(self.scene)
        self.scene.find("root/hammer1").reparentTo(self.scene)

        self.barrel = self.scene.find("barrel")
        self.barrel.setPos(self.scene, 0, 0, 0)

        self.setupCollision()

        base.enableParticles()
        gravityFN = ForceNode('world-forces')
        gravityFNP = render.attachNewNode(gravityFN)
        gravityForce = LinearVectorForce(0, 0, -9.81)  #gravity acceleration
        gravityFN.addForce(gravityForce)
        base.physicsMgr.addLinearForce(gravityForce)

        return Task.done

    def createBarrel(self):

        barrelNode = NodePath("PhysicalBarrel")
        barrelNode.reparentTo(self.scene)

        physicsBarrel = ActorNode("physics_barrel")
        physicsBarrel.getPhysicsObject().setMass(
            0.01)  #in what units? (69 kindda 3 lbs)
        barrel = barrelNode.attachNewNode(physicsBarrel)
        base.physicsMgr.attachPhysicalNode(physicsBarrel)

        barrel.setPos(0, 0, 2)

        visual_barrel = self.scene.attachNewNode("BarrelCopy")
        originalBarrel = self.scene.find("barrel")
        originalBarrel.instanceTo(visual_barrel)
        visual_barrel.reparentTo(barrel)

        sphere = CollisionSphere(6.6, 0, 4.78, 0.5)
        cnodePath = visual_barrel.attachNewNode(
            CollisionNode('barrelCollider'))
        cnodePath.node().addSolid(sphere)
        cnodePath.node().setFromCollideMask(
            0xD)  # crash with default and mario body and walls
        cnodePath.node().setIntoCollideMask(
            0xD)  # crash with default and mario body and walls
        cnodePath.show()
        self.physicsCollisionPusher.addCollider(cnodePath, barrel)
        base.cTrav.addCollider(cnodePath, self.physicsCollisionPusher)

        barrelForceNode = ForceNode('barrelForce')
        barrel.attachNewNode(barrelForceNode)
        barrelForce = LinearVectorForce(-7, 0, 0, 1, False)
        # barrelForce.setMassDependent(0)
        barrelForceNode.addForce(barrelForce)
        physicsBarrel.getPhysical(0).addLinearForce(barrelForce)

    def setupBoxCollider(self,
                         node,
                         px,
                         py,
                         pz,
                         w,
                         d,
                         h,
                         nm,
                         colliderEventHandler,
                         fromCollisionMask=0,
                         intoCollisionMask=0):

        hitBox = CollisionBox(Point3(px, py, pz), w, d, h)
        cnodePath = node.attachNewNode(CollisionNode(nm))
        cnodePath.node().addSolid(hitBox)
        cnodePath.node().setIntoCollideMask(intoCollisionMask)
        cnodePath.node().setFromCollideMask(fromCollisionMask)
        cnodePath.show()
        base.cTrav.addCollider(cnodePath, colliderEventHandler)

    def setupCollision(self):
        base.cTrav = CollisionTraverser()
        self.collisionHandlerEvent = CollisionHandlerEvent()
        self.physicsCollisionPusher = PhysicsCollisionHandler()

        self.collisionHandlerEvent.addInPattern('into-%in')
        self.collisionHandlerEvent.addOutPattern('outof-%in')

        # create masks
        defaultCollisionMask = BitMask32(0b0001)  #0x1
        segmentCollisionMask = BitMask32(0b1000)  #0x8
        stairsCollisionMask = BitMask32(0b0010)  #0x2
        marioBodyCollisionMask = BitMask32(0b0011)  #0x3
        collisionWallsForBarrels = BitMask32(0b0100)  #0x4

        # mario segment collider
        ray = CollisionSegment(7, 0, -4.5, 7, 0, -5.1)
        cnodePath = self.mario.attachNewNode(CollisionNode('marioRay'))
        cnodePath.node().addSolid(ray)
        cnodePath.node().setFromCollideMask(segmentCollisionMask)
        cnodePath.node().setIntoCollideMask(0)
        cnodePath.show()
        base.cTrav.addCollider(cnodePath, self.collisionHandlerEvent)

        self.setupBoxCollider(self.mario, 7, 0, -4.5, 0.5, 5, 0.5,
                              'marioHitBox', self.collisionHandlerEvent,
                              marioBodyCollisionMask, marioBodyCollisionMask)

        stairs1 = self.scene.find("bottomstair")
        self.setupBoxCollider(stairs1, -6.8, 0, -3.0, 0.5, 5, 2.5,
                              'stairs1HitBox', self.collisionHandlerEvent,
                              stairsCollisionMask, stairsCollisionMask)

        stairs2 = self.scene.find("middlestair")
        self.setupBoxCollider(stairs2, -0.86, 0, .1, 0.5, 5, 2.1,
                              'stairs2HitBox', self.collisionHandlerEvent,
                              stairsCollisionMask, stairsCollisionMask)

        stairs3 = self.scene.find("topstair")
        self.setupBoxCollider(stairs3, -6.8, 0, 3.1, 0.5, 5, 2.2,
                              'stairs3HitBox', self.collisionHandlerEvent,
                              stairsCollisionMask, stairsCollisionMask)

        hammer = self.scene.find("MainGroup")  # hammer
        self.setupBoxCollider(hammer, 5.5, 0, -1.5, 0.5, 5, 0.5,
                              'hammer1HitBox', self.collisionHandlerEvent,
                              stairsCollisionMask, stairsCollisionMask)

        dk = self.scene.find("hammer1")
        self.setupBoxCollider(dk, 8.7, 0, 5, 1, 5, 1, 'dkHitBox',
                              self.collisionHandlerEvent, stairsCollisionMask,
                              stairsCollisionMask)

        floor0 = self.scene.find("floor0")
        self.setupBoxCollider(floor0,
                              -2.5,
                              0,
                              -5.5,
                              10,
                              5,
                              0.5,
                              'floor0HitBox',
                              self.collisionHandlerEvent,
                              intoCollisionMask=segmentCollisionMask)

        floor1 = self.scene.find("floor1")
        self.setupBoxCollider(floor1,
                              2,
                              0,
                              -2.5,
                              8.4,
                              5,
                              0.5,
                              'floor1HitBox',
                              self.collisionHandlerEvent,
                              intoCollisionMask=segmentCollisionMask)
        floor2_1 = self.scene.find("floor2")
        self.setupBoxCollider(floor2_1,
                              3.6,
                              0,
                              0.5,
                              3.8,
                              5,
                              0.5,
                              'floor21HitBox',
                              self.collisionHandlerEvent,
                              intoCollisionMask=segmentCollisionMask)
        floor2_2 = self.scene.find("pCube4")
        self.setupBoxCollider(floor2_2,
                              -6.3,
                              0,
                              0.5,
                              5.0,
                              5,
                              0.5,
                              'floor22HitBox',
                              self.collisionHandlerEvent,
                              intoCollisionMask=segmentCollisionMask)
        floor3 = self.scene.find("floors")
        self.setupBoxCollider(floor3,
                              1.8,
                              0,
                              3.5,
                              8,
                              5,
                              0.5,
                              'floor3HitBox',
                              self.collisionHandlerEvent,
                              intoCollisionMask=segmentCollisionMask)

        rightWall = self.scene.find("rightWall")
        self.setupBoxCollider(rightWall,
                              -12,
                              0,
                              0,
                              1,
                              5,
                              10,
                              'rightWallHitBox',
                              self.collisionHandlerEvent,
                              fromCollisionMask=collisionWallsForBarrels,
                              intoCollisionMask=collisionWallsForBarrels)

        leftWall = self.scene.find("walls")
        self.setupBoxCollider(leftWall,
                              11.5,
                              0,
                              0,
                              1,
                              5,
                              10,
                              'leftWallHitBox',
                              self.collisionHandlerEvent,
                              fromCollisionMask=collisionWallsForBarrels,
                              intoCollisionMask=collisionWallsForBarrels)

        barrelFixer = self.scene.attachNewNode("barrelFixer")
        self.setupBoxCollider(barrelFixer,
                              -3,
                              0,
                              0.505,
                              10,
                              5,
                              0.5,
                              'barrelFixerHitBox',
                              self.collisionHandlerEvent,
                              fromCollisionMask=collisionWallsForBarrels,
                              intoCollisionMask=collisionWallsForBarrels)

        barrelDestroyer = self.scene.attachNewNode("barrelDestroyer")
        self.setupBoxCollider(barrelDestroyer,
                              0,
                              0,
                              -8,
                              15,
                              5,
                              0.5,
                              'barrelDestroyerHitBox',
                              self.collisionHandlerEvent,
                              fromCollisionMask=collisionWallsForBarrels,
                              intoCollisionMask=collisionWallsForBarrels)

        self.accept('into-stairs1HitBox', self.enableStair)
        self.accept('outof-stairs1HitBox', self.disableStair)
        self.accept('into-stairs2HitBox', self.enableStair)
        self.accept('outof-stairs2HitBox', self.disableStair)
        self.accept('into-stairs3HitBox', self.enableStair)
        self.accept('outof-stairs3HitBox', self.disableStair)
        self.accept('into-hammer1HitBox', self.enableHammer)
        self.accept('into-dkHitBox', self.dkArrived)

        self.accept('into-floor0HitBox', self.enableJump)
        self.accept('outof-floor0HitBox', self.disableJump)
        self.accept('into-floor1HitBox', self.enableJump)
        self.accept('outof-floor1HitBox', self.disableJump)
        self.accept('into-floor21HitBox', self.enableJump)
        self.accept('outof-floor21HitBox', self.disableJump)
        self.accept('into-floor22HitBox', self.enableJump)
        self.accept('outof-floor22HitBox', self.disableJump)
        self.accept('into-floor3HitBox', self.enableJump)
        self.accept('outof-floor3HitBox', self.disableJump)

        self.accept("into-barrelCollider", self.barrelCrash)

        base.cTrav.showCollisions(self.render)

    def dkArrived(self, evt):
        if (self.hammer):
            self.scene.node().removeChild(
                evt.getIntoNodePath().node().getParent(0))
        else:
            self.floorValidPosition = 0
            self.mario.setPos(self.scene, self.marioInitialPos)
            text = DirectLabel(text="Game Over", text_scale=(0.5, 0.5))

    def enableHammer(self, evt):
        print(f"{evt.getIntoNodePath()}{evt.getFromNodePath()}")
        self.scene.node().removeChild(
            evt.getIntoNodePath().node().getParent(0))
        self.hammer = True

    def changeBarrelDirection(self, evt):
        print(f"Changing barrel direction {evt}")

    def barrelCrash(self, evt):
        barrel = evt.getIntoNodePath().node().getParent(0).getParent(0)
        other = evt.getFromNodePath().node().getParent(0)

        parents = barrel.parents
        print(f"{other}")

        if other.name == "barrelDestroyer":
            p = parents[0]
            self.scene.node().removeChild(p)
            return

        if not (other == self.mario.node() or other.name == "barrelFixer"):
            forceNode = barrel.getChildren()[1]
            actualForce = forceNode.getForce(0)
            actualForce.setVector(actualForce.getLocalVector().x * -1, 0, 0)
            forceNode.clear()
            forceNode.addForce(actualForce)

        if (other == self.mario.node()):
            if not self.hammer:
                self.lifes = self.lifes - 1
                self.floorValidPosition = 0
                self.mario.setPos(self.scene, self.marioInitialPos)

            p = parents[0]
            self.scene.node().removeChild(p)

            if (self.lifes < 0):
                print("game over dude!!")
                text = DirectLabel(text="Game Over", text_scale=(0.5, 0.5))

    def enableStair(self, evt):
        print("crashed mario and stair")
        self.canClimb = True

    def disableStair(self, evt):
        print("exit mario and stair")
        self.canClimb = False

    def enableJump(self, evt):
        self.isGrounded = True
        print("enable jump")
        # fromCollider =  evt.getFrom().getCenter().z - evt.getFrom().getDimensions().z/2
        self.floorValidPosition = evt.getInto().getCenter().z + 5.5
        #print(f"{ evt.getInto().getCenter().z } {self.floorValidPosition} ")

    def disableJump(self, evt):
        print("disable jump")
        self.isGrounded = False

    def pressUp(self):
        print("up enabled")
        self.input["up"] = True

    def stopUp(self):
        print("up disabled")
        self.input["up"] = False

    def pressRight(self):
        self.input["right"] = True

    def stopRight(self):
        self.input["right"] = False

    def pressLeft(self):
        self.input["left"] = True

    def stopLeft(self):
        self.input["left"] = False

    def pressSpace(self):
        self.input["space"] = True
        self.camera.setPos(0, 30, 0)
        self.camera.lookAt(self.scene)

    def stopSpace(self):
        self.input["space"] = False

    def getAdvance(self):
        if self.input["left"] and self.input["right"]:
            return 0
        if self.input["left"]:
            return -1
        if self.input["right"]:
            return 1
        return 0

    def applyJump(self):
        jz = 0  # jump Y/Z
        vi = 4  # initial velocity
        g = -6  # gravity

        if (self.isGrounded):
            if (self.canJump):
                if (self.input["space"]):
                    self.jumpTime = 0.1
                    self.canJump = False
                    self.vyi = vi
                    jz = self.vyi * self.jumpTime + 0.5 * g * self.jumpTime * self.jumpTime
                    vz = self.vyi + g * self.jumpTime
                else:
                    return 0
            else:
                self.jumpTime = self.jumpTime + globalClock.getDt()
                jz = self.vyi * self.jumpTime + 0.5 * g * self.jumpTime * self.jumpTime
                vz = self.vyi + g * self.jumpTime
                if vz < 0:  #finished
                    self.jumpTime = 0
                    self.canJump = True
                    self.vyi = 0
                    jz = 0
        else:
            if (not self.isClimbing):
                self.canJump = False
                self.jumpTime = self.jumpTime + globalClock.getDt()
                jz = self.vyi * self.jumpTime + 0.5 * g * self.jumpTime * self.jumpTime
                vz = self.vyi + g * self.jumpTime

        return jz

    def applyStairs(self, pz):
        if (self.canClimb):
            if (self.input["up"]):
                self.isClimbing = True

        if (self.isClimbing):
            if (self.input["up"]):
                return pz + 0.1
        if (not self.canClimb):
            self.isClimbing = False

        return pz

    def update(self, task):
        self.camera.setPos(0, 30, 0)
        self.camera.lookAt(self.scene)
        pz = self.applyJump()

        if (self.posNotInitialized):
            self.marioInitialPos = self.mario.getPos()
            self.posNotInitialized = False

        self.barrelTimer = self.barrelTimer + globalClock.getDt()
        if self.barrelTimer > (3 + random() * 2):
            self.createBarrel()
            self.barrelTimer = 0

        # self.mario.getPos(self.render).z
        advZ = self.applyStairs(self.floorValidPosition)
        self.floorValidPosition = advZ
        #print(f' {self.mario.getPos(self.render).z} {self.floorValidPosition}  ')
        self.mario.setPos(self.render,
                          self.mario.getPos().x + -self.getAdvance() * .1, 0,
                          advZ + pz)
        return Task.cont
예제 #22
0
class TunnelPinchTask(ShowBase, GripStateMachine):
    DATA_DIR = 'data'
    
    def __init__(self, id, session, hand, block, mode, wrist):
        ShowBase.__init__(self)
        GripStateMachine.__init__(self)
        base.disableMouse()
        wp = WindowProperties()
        wp.setSize(1920,1080)
        wp.setFullscreen(True)
        wp.setUndecorated(True)
        base.win.requestProperties(wp)

        self.sub_id = str(id)
        self.sess_id = str(session)
        self.hand = str(hand)
        self.block = str(block)
        self.mode = str(mode)
        self.wrist = str(wrist)
        
        self.prev_blk = os.path.join(self.DATA_DIR,'exp_2',self.sub_id,self.sess_id,self.wrist,self.hand,"B0")
        self.exp_blk0 = os.path.join(self.DATA_DIR,'exp_1',self.sub_id,self.sess_id,self.wrist,self.hand,"B0")
        self.table = np.loadtxt('src/tunnel_pinch_task/trialtable_flex.csv',dtype='str',delimiter=',',skiprows=1)

        indices = {}
        try:
            self.prev_table = np.loadtxt(os.path.join(self.prev_blk, 'final_targets.csv'),dtype='str',delimiter=',',skiprows=1)
        except:
            try:
                self.prev_table = np.loadtxt(os.path.join(self.exp_blk0, 'final_targets.csv'),dtype='str',delimiter=',',skiprows=1)
            except:
                print('Previous target file not found, results may be suboptimal')
        try:
            for i in range(self.prev_table.shape[0]):
                indices[self.prev_table[i,1]] = int(self.prev_table[i,0])-1
            for i in range(self.table.shape[0]):
                self.table[i,11] = self.prev_table[indices[self.table[i,1].strip()],11]
                self.table[i,12] = self.prev_table[indices[self.table[i,1].strip()],12]
                self.table[i,13] = self.prev_table[indices[self.table[i,1].strip()],13]
        except:
            print('Invalid target file')
        
        self.table = np.array([[item.strip() for item in s] for s in self.table])

        ###################################################
        #only use rows relevant to this block
        #HARDCODED! NOTE IN LOG SHEET
        spec_table = []
        for i in range(self.table.shape[0]):
            if int(self.block)%5 == 0: #block 0 to adjust positions
                if "(p)" in self.table[i,2]:
                    spec_table.append(self.table[i])
            elif int(self.block)%5 == 1:
                if "(L)" in self.table[i,2]:
                    spec_table.append(self.table[i])
            elif int(self.block)%5 == 2:
                if "(L+t)" in self.table[i,2]:
                    spec_table.append(self.table[i])
            elif int(self.block)%5 == 3:
                if "(S)" in self.table[i,2]:
                    spec_table.append(self.table[i])
            elif int(self.block)%5 == 4:
                if "(S+t)" in self.table[i,2]:
                    spec_table.append(self.table[i])
        ###################################################
        self.table = np.array(spec_table)

        self.session_dir = os.path.join(self.DATA_DIR,'exp_2',self.sub_id,self.sess_id,self.wrist,self.hand)
        self.subjinfo = self.sub_id + '_' + self.sess_id + '_' + self.hand + '_log.yml'
        self.p_x,self.p_y,self.p_a = GET_POS(self.session_dir,self.subjinfo,self.hand,self.wrist)

        self.rotmat = ROT_MAT(self.p_a,self.hand)

        self.setup_text()
        self.setup_lights()
        self.setup_camera()
        
        self.trial_counter = 0
        self.load_models()
        self.load_audio()
        self.update_trial_command()
        self.countdown_timer = CountdownTimer()
        self.hold_timer = CountdownTimer()

        self.cTrav = CollisionTraverser()
        self.chandler = CollisionHandlerEvent()
        self.chandler.addInPattern('%fn-into-%in')
        self.chandler.addOutPattern('%fn-outof-%in')
        self.chandler.addAgainPattern('%fn-again-%in')
        self.attachcollnodes()

        taskMgr.add(self.read_data, 'read')
        for i in range(5):
            taskMgr.add(self.move_player, 'move%d' % i, extraArgs = [i], appendTask=True)
        taskMgr.add(self.log_data, 'log_data')
        taskMgr.add(self.update_state, 'update_state', sort=1)

        self.accept('space', self.space_on)
        self.accept('escape', self.clean_up)
        self.space = False
        self.statenum = list()

        self.max_time = 20
        self.med_data = None

        self.grip_dir = os.path.join(self.DATA_DIR,'exp_2',self.sub_id,self.sess_id,self.wrist,self.hand,"B"+self.block)
        if not os.path.exists(self.grip_dir):
           print('Making new folders: ' + self.grip_dir)
           os.makedirs(self.grip_dir)

        self.dev = MpDevice(RightHand(calibration_files=['calibs/cal_mat_70_v2.mat',
                                                'calibs/cal_mat_73_v2.mat',
                                                'calibs/cal_mat_56.mat',
                                                'calibs/cal_mat_58_v2.mat',
                                                'calibs/cal_mat_50.mat'], clock=mono_clock.get_time))

    ############
    #SET UP HUD#
    ############
    def setup_text(self):
        self.bgtext = OnscreenText(text='Not recording.', pos=(-0.8, 0.8),
                                 scale=0.08, fg=(0, 0, 0, 1),
                                 bg=(1, 1, 1, 1), frame=(0.2, 0.2, 0.8, 1),
                                 align=TextNode.ACenter)
        self.bgtext.reparentTo(self.aspect2d)

        self.dirtext = OnscreenText( pos=(-0.6, 0.65),
                                 scale=0.08, fg=(0, 0, 0, 1),
                                 bg=(1, 1, 1, 1), frame=(0.2, 0.2, 0.8, 1),
                                 align=TextNode.ACenter)
        self.dirtext.reparentTo(self.aspect2d)
    
    ##########################
    #SET UP SCENE AND PLAYERS#
    ##########################
    def setup_lights(self):
        pl = PointLight('pl')
        pl.setColor((1, 1, 1, 1))
        plNP = self.render.attachNewNode(pl)
        plNP.setPos(-10, -10, 10)
        self.render.setLight(plNP)
        pos = [[[0, 0, 50], [0, 0, -10]],
               [[0, -50, 0], [0, 10, 0]],
               [[-50, 0, 0], [10, 0, 0]]]
        for i in pos:
            dl = Spotlight('dl')
            dl.setColor((1, 1, 1, 1))
            dlNP = self.render.attachNewNode(dl)
            dlNP.setPos(*i[0])
            dlNP.lookAt(*i[1])
            dlNP.node().setShadowCaster(False)
            self.render.setLight(dlNP)

    def setup_camera(self):
        self.cam.setPos(0, 0, 12)
        self.cam.lookAt(0, 2, 0)
        self.camLens.setFov(90)

    def load_models(self):
        self.back_model = self.loader.loadModel('models/back')
        self.back_model.setScale(10, 10, 10)
        if self.hand == "Left":
            self.back_model.setH(90)
        self.back_model.reparentTo(self.render)

        self.player_offsets = [[self.p_x[0]-5, self.p_y[0]+3, 0], [self.p_x[1]-2.5, self.p_y[1]+4.5, 0], [self.p_x[2], self.p_y[2]+5, 0],
                                [self.p_x[3]+2.5, self.p_y[3]+4.5, 0], [self.p_x[4]+5, self.p_y[4]+3, 0]]
        self.p_col =[[0,0,250],[50,0,200],[125,0,125],[200,0,50],[250,0,0]]
        if self.hand == 'Left':
            self.p_col = self.p_col[::-1]

        self.players = list()
        self.contacts = list()        
        for counter, value in enumerate(self.player_offsets):
            self.players.append(self.loader.loadModel('models/target'))
            self.contacts.append(False)

            self.players[counter].setPos(*value)
            self.players[counter].setScale(0.2, 0.2, 0.2)
            self.players[counter].setColorScale(
                self.p_col[counter][0]/255, self.p_col[counter][1]/255, self.p_col[counter][2]/255, 1)
            self.players[counter].reparentTo(self.render)
            self.players[counter].show()

        self.target_select()

    def load_audio(self):
        self.pop = self.loader.loadSfx('audio/Blop.wav')
        self.buzz = self.loader.loadSfx('audio/Buzzer.wav')


    ############################
    #SET UP COLLISION MECHANICS#
    ############################
    def attachcollnodes(self):
        self.inside = [False]*5
        for i in range(5):
            self.fromObject = self.players[i].attachNewNode(CollisionNode('colfromNode'+str(i)))
            self.fromObject.node().addSolid(CollisionSphere(0,0,0,1))
            self.cTrav.addCollider(self.fromObject, self.chandler)

        for i in range(5):
            self.accept('colfromNode%d-into-colintoNode' % i, self.collide1,[i])
            self.accept('colfromNode%d-again-colintoNode' % i, self.collide2,[i])
            self.accept('colfromNode%d-outof-colintoNode' % i, self.collide3,[i])

    def collide1(self,f,collEntry):
        if f in self.highlighted_indices:
            self.players[f].setColorScale(0,1,0,1)
            self.tar.setColorScale(0.2,0.2,0.2,1)
            self.tar.setAlphaScale(0.7)
            self.contacts[f] = True
            taskMgr.doMethodLater(self.delay,self.too_long,'too_long%d' % f,extraArgs = [f])
                
    def collide2(self,f,collEntry):
        for i in self.highlighted_indices:
            if self.contacts[i] == False:
                return
        taskMgr.remove('too_long%d' % f)

    def collide3(self,f,collEntry):
        taskMgr.remove('too_long%d' % f)
        self.reset_fing(f)
        self.tar.setColorScale(0.1,0.1,0.1,1)
        self.tar.setAlphaScale(0.7)

    def too_long(self,f):
        self.reset_fing(f)
        self.tar.setColorScale(0.5,0.2,0.2,1)
        self.tar.setAlphaScale(0.7)

    def reset_fing(self,f):
        self.players[f].setColorScale(
                self.p_col[f][0]/255, self.p_col[f][1]/255, self.p_col[f][2]/255, 1)
        self.contacts[f] = False

    ###############
    #TARGET THINGS#
    ###############
    def show_target(self):
        self.target_select()
        self.intoObject = self.tar.attachNewNode(CollisionNode('colintoNode'))

        if self.table[self.trial_counter,7] == "sphere":
            self.intoObject.node().addSolid(CollisionSphere(0,0,0,1))
        elif self.table[self.trial_counter,7] == "cylinder":
            self.intoObject.node().addSolid(CollisionTube(0,0,-2,0,0,2,1))
        else:
            raise NameError("No such collision type")

        self.tar.show()
        self.occSolid.show()
        self.occLines.show()

        for i in range(5):
            if i not in self.highlighted_indices:
                self.players[i].hide()

    def target_select(self):
        self.tgtscx=float(self.table[self.trial_counter,14])
        self.tgtscy=float(self.table[self.trial_counter,15])
        self.tgtscz=float(self.table[self.trial_counter,16])
        tgttsx=float(self.table[self.trial_counter,11])
        tgttsy=float(self.table[self.trial_counter,12])
        tgttsz=float(self.table[self.trial_counter,13])
        tgtrx=float(self.table[self.trial_counter,17])
        tgtry=float(self.table[self.trial_counter,18])
        tgtrz=float(self.table[self.trial_counter,19])
        if self.hand == 'Left':
            tgttsx *= -1
            tgtrx *= -1

        self.static_task = (str(self.table[self.trial_counter,5]) == "True")
        self.target_model = str(self.table[self.trial_counter,6])
        self.highlighted_indices=[int(s)-1 for s in self.table[self.trial_counter,4].split(' ')]
        if self.hand == 'Left':
            self.highlighted_indices=[4-i for i in self.highlighted_indices]

        self.tgtposx = np.mean(np.asarray(self.player_offsets)[self.highlighted_indices][[-2,-1],0]) + tgttsx
        self.tgtposy = np.mean(np.asarray(self.player_offsets)[self.highlighted_indices][[0,1],1]) + tgttsy
        if self.hand == 'Left':
            self.tgtposx = np.mean(np.asarray(self.player_offsets)[self.highlighted_indices][[0,1],0]) + tgttsx
            self.tgtposy = np.mean(np.asarray(self.player_offsets)[self.highlighted_indices][[-2,-1],1]) + tgttsy
        #self.tgtposx = np.mean(np.asarray(self.player_offsets)[self.highlighted_indices][:,0])
        #self.tgtposy = np.mean(np.asarray(self.player_offsets)[self.highlighted_indices][:,1])
        self.tgtposz = np.mean(np.asarray(self.player_offsets)[self.highlighted_indices][:,2]) + tgttsz
        
        self.tar = self.loader.loadModel(self.target_model)
        self.tar.setScale(self.tgtscx,self.tgtscy,self.tgtscz)
        self.tar.setPos(self.tgtposx,self.tgtposy,self.tgtposz)
        self.tar.setHpr(tgtrx,tgtry,tgtrz)
        self.tar.setColorScale(0.1, 0.1, 0.1, 1)
        self.tar.setAlphaScale(0.7)
        self.tar.setTransparency(TransparencyAttrib.MAlpha)
        self.tar.reparentTo(self.render)
        self.tar.hide()

        if len(self.highlighted_indices) == 2:
            dx = self.players[self.highlighted_indices[0]].getX() - self.players[self.highlighted_indices[1]].getX()
            dy = self.players[self.highlighted_indices[0]].getY() - self.players[self.highlighted_indices[1]].getY()
            angle = math.degrees(math.atan(dy/dx))
            self.table[self.trial_counter,9] =  str(angle) + ' ' + str(angle-180)
        
        self.angs=self.table[self.trial_counter,9].split(' ')
        self.angs = [float(a) for a in self.angs]
        self.tunn_width=float(self.table[self.trial_counter,10])
        self.r = 1.5
        if int(self.block) == 0:
            self.r = 0
        self.x = [self.r*math.cos(math.radians(a)) for a in self.angs]
        self.y = [self.r*math.sin(math.radians(a)) for a in self.angs]
        self.occ = draw_shape(self.angs,self.tunn_width,self.r)
        self.occSolid = render.attachNewNode(self.occ[0])
        self.occSolid.setPos(self.tgtposx,self.tgtposy,self.tgtposz)
        self.occSolid.setColorScale(0,1,1,0)
        self.occSolid.setTransparency(TransparencyAttrib.MAlpha)
        self.occSolid.setAlphaScale(0.6)
        self.occLines = render.attachNewNode(self.occ[1])
        self.occLines.setPos(self.tgtposx,self.tgtposy,self.tgtposz)
        self.occSolid.hide()
        self.occLines.hide()
        self.delay=float(self.table[self.trial_counter,8])

        self.distances = [[0,0,0],[0,0,0],[0,0,0],[0,0,0],[0,0,0]]

        #change camera to be on top of target
        self.cam.setPos(self.tgtposx, self.tgtposy - 2, 12)
        self.back_model.setPos(self.tgtposx,self.tgtposy - 2,0)
        self.cam.lookAt(self.tgtposx, self.tgtposy, 0)

    ##############
    #MOVE FINGERS#
    ##############
    def read_data(self,task):
        error, data = self.dev.read()
        if data is not None:
            data *= 0.001
            self.ts = data.time
            data = np.dot(data,self.rotmat)
            self.data = data
            if self.med_data is None:
                self.med_data = np.median(data, axis=0)

            if self.space:
                self.statenum.extend(([self.checkstate()])*len(data.time))
                
        return task.cont
        
    def move_player(self,p,task):
        if self.data is not None :
            k = p*3
            new_x = 10*np.mean(self.data[-1,k]) + self.player_offsets[p][0] - 10*self.med_data[k]
            new_y = 10*np.mean(self.data[-1,k + 1]) + self.player_offsets[p][1] - 10*self.med_data[k + 1]
            new_z = 10*np.mean(self.data[-1,k + 2]) + self.player_offsets[p][2] - 10*self.med_data[k + 2]

            #make sure digits do not cross each other
            if ((p in range(1,3) and p+1 in self.highlighted_indices and new_x > self.players[p+1].getX())
                or (p in range(2,4) and p-1 in self.highlighted_indices and new_x < self.players[p-1].getX())):
                    new_x = self.players[p].getX()
            
            #make sure digits do not cross into target
            if self.space == True and p in self.highlighted_indices:
                self.distances[p][0] = new_x - self.tar.getX()
                self.distances[p][1] = new_y - self.tar.getY()
                self.distances[p][2] = new_z - self.tar.getZ()
                self.check_pos(p)
                
            self.players[p].setPos(new_x, new_y, new_z)
            
        return task.cont
    
    def check_pos(self, p):
        x = self.distances[p][0]
        y = self.distances[p][1]
        z = self.distances[p][2]
        hit = True
        for i in range(len(self.angs)):
            p_ang = math.acos((x*self.x[i]+y*self.y[i])/(self.r*(x**2+y**2)**0.5))
            if math.sin(p_ang)*(x**2+y**2)**0.5 < self.tunn_width and p_ang < math.pi/2:
                hit = False
                break
        if (abs(z) <= 1.2 #check z location
            and x**2 + y**2 <= self.r**2 #within radius of circle
            and hit == True):
                if self.inside[p] is False:
                    self.ignore('colfromNode%d-into-colintoNode' % p)
                    self.ignore('colfromNode%d-again-colintoNode' % p)
                    self.players[p].setColorScale(1,1,0,1)
                    self.inside[p] = True
        else:
            if self.inside[p] is True and x**2 + y**2 > self.r**2:
                self.accept('colfromNode%d-into-colintoNode' % p, self.collide1,[p])
                self.accept('colfromNode%d-again-colintoNode' % p, self.collide2,[p])
                self.players[p].setColorScale(
                    self.p_col[p][0]/255, self.p_col[p][1]/255, self.p_col[p][2]/255, 1)
                self.inside[p] = False

    ##################
    #CHECK COMPLETION#
    ##################
    def close_to_target(self):
        for i in self.highlighted_indices:
            if self.contacts[i] == False:
                return False

        self.tar.setColorScale(0,1,1,1)
        return True

    def check_hold(self):
        if not self.close_to_target():
            self.hold_timer.reset(0.5)
            return False
        return self.hold_timer.elapsed() < 0

    def adjust_targets(self):
        #no adjustment if more than 2 fingers or position is prone
        if len(self.highlighted_indices) > 2 or self.wrist == 'pron':
            return

        xadj,yadj,zadj = np.mean(np.asarray(self.distances)[self.highlighted_indices],0)
        #xadj = np.mean(np.asarray(self.distances)[self.highlighted_indices][0])
        #yadj = np.mean(np.asarray(self.distances)[self.highlighted_indices][1])
        #zadj = np.mean(np.asarray(self.distances)[self.highlighted_indices][2])

        #do adjustment on all tasks with same name
        if self.hand == 'Left':
            xadj = -xadj
        for i in range(self.trial_counter+1,self.table.shape[0]):
            if self.table[i,1] == self.table[self.trial_counter,1]:
                self.table[i,11] = float(self.table[i,11]) + xadj
                self.table[i,12] = float(self.table[i,12]) + yadj
                self.table[i,13] = float(self.table[i,13]) + zadj
    
    #########
    #LOGGING#
    #########
    def play_success(self):
        if int(self.block) == 0:
            self.adjust_targets()
        self.pop.play()
        self.tar.hide()
        self.highlighted_indices = [0,1,2,3,4]

    def log_text(self):
        self.bgtext.setText('Now logging...')

    def log_data(self, task):
        if (self.trial_counter + 1) <= self.table.shape[0]:
            if self.space:
                self.log_file_name = os.path.join(self.grip_dir,
                                          self.sub_id+"_"+self.sess_id+"_"+self.hand+"_"+
                                              str(self.table[self.trial_counter,1])+"_"+str(self.table[self.trial_counter,0])+".csv" )
                self.movvars = np.column_stack((self.ts, self.statenum, self.data))
                self.statenum = []
                if self.mode=='task':
                    with open(self.log_file_name, 'ab') as f:
                        np.savetxt(f, self.movvars, fmt='%10.5f', delimiter=',')
            return task.cont
        else:
            pass

    def stoplog_text(self):
        self.dirtext.clearText()
        self.bgtext.setText('Done logging!')
        for i in range(5):
            self.players[i].show()

    #######
    #RESET#
    #######
    def delete_file(self):
        if (self.trial_counter + 1) <= self.table.shape[0]:
            self.log_file_name = os.path.join(self.grip_dir,
                                      self.sub_id+"_"+self.sess_id+"_"+self.hand+"_"+
                                          str(self.table[self.trial_counter,1])+"_"+str(self.table[self.trial_counter,0])+".csv" )
            try:
                os.remove(self.log_file_name)
            except OSError:
                pass
        else:
            pass

    def reset_baseline(self):
       self.med_data = None
                   
    def reset_keyboard_bool(self):
        self.space = False

    def hide_target(self):
        self.tar.hide()
        self.occSolid.hide()
        self.occLines.hide()
        self.intoObject.removeNode()
        self.imageObject.destroy()

    def update_trial_command(self):
        self.dirtext.setText(str(self.table[self.trial_counter,2]))
        if self.hand == 'Left':
            xfac = -0.25
        else:
            xfac = 0.25
        self.imageObject = OnscreenImage(image = str(self.table[self.trial_counter,3]),scale=(xfac,0.25,0.25),pos=(-0.8, 0, 0.3))

    def increment_trial_counter(self):
        self.trial_counter += 1
        self.update_trial_command()

    ########
    #TIMERS#
    ########
    def start_trial_countdown(self):
        self.countdown_timer.reset(self.max_time)

    def start_hold_countdown(self):
        self.hold_timer.reset(0.5)

    def start_post_countdown(self):
        self.countdown_timer.reset(2)

    def time_elapsed(self):
        return self.countdown_timer.elapsed() < 0

    #########
    #MACHINE#
    #########
    def update_state(self, task):
        self.step()
        return task.cont

    def wait_for_space(self):
        return self.space

    def space_on(self):
        self.space = True

    #####
    #END#
    #####
    def trial_counter_exceeded(self):
        return (self.trial_counter+1) > self.table.shape[0]-1

    def clean_up(self):
        #write last known positions to 'final_targets' file
        f = open('src/pinch_task/trialtable_flex.csv')
        header = f.readline().rstrip()
        np.savetxt(self.grip_dir + '/final_targets.csv',self.table,fmt='%s',header = header, delimiter=',')
        f.close()
        sys.exit()
예제 #23
0
파일: events.py 프로젝트: NanoDano/cookbook
class World(DirectObject):
 
    def __init__( self ):
        # Initialize the traverser.
        base.cTrav = CollisionTraverser()
 
        # Initialize the handler.
        self.collHandEvent = CollisionHandlerEvent()
        self.collHandEvent.addInPattern('into-%in')
        self.collHandEvent.addOutPattern('outof-%in')
 
        # Make a variable to store the unique collision string count.
        self.collCount = 0
 
        # Load a model. Reparent it to the camera so we can move it.
        s = loader.loadModel('smiley')	
        s.reparentTo(camera)
        s.setPos(0, 25, 0)
 
        # Setup a collision solid for this model.
        sColl = self.initCollisionSphere(s, True)
 
        # Add this object to the traverser.
        base.cTrav.addCollider(sColl[0], self.collHandEvent)
 
        # Accept the events sent by the collisions.
        self.accept('into-' + sColl[1], self.collide3)
        self.accept('outof-' + sColl[1], self.collide4)
        print(sColl[1])
 
        # Load another model.
        t = loader.loadModel('smiley')
        t.reparentTo(render)
        t.setPos(5, 25, 0)
 
        # Setup a collision solid for this model.
        tColl = self.initCollisionSphere(t, True)
 
        # Add this object to the traverser.
        base.cTrav.addCollider(tColl[0], self.collHandEvent)
 
        # Accept the events sent by the collisions.
        self.accept('into-' + tColl[1], self.collide)
        self.accept('outof-' + tColl[1], self.collide2)
        print(tColl[1])
 
        print("WERT")
 
    def collide(self, collEntry):
        print("WERT: object has collided into another object")
        Sequence(Func(collEntry.getFromNodePath().getParent().setColor,
                      VBase4(1, 0, 0, 1)),
                 Wait(0.2),
                 Func(collEntry.getFromNodePath().getParent().setColor,
                      VBase4(0, 1, 0, 1)),
                 Wait(0.2),
                 Func(collEntry.getFromNodePath().getParent().setColor,
                      VBase4(1, 1, 1, 1))).start()
 
 
    def collide2(self, collEntry):
        print("WERT.: object is no longer colliding with another object")
 
    def collide3(self, collEntry):
        print("WERT2: object has collided into another object")
 
    def collide4(self, collEntry):
        print("WERT2: object is no longer colliding with another object")
 
    def initCollisionSphere(self, obj, show=False):
        # Get the size of the object for the collision sphere.
        bounds = obj.getChild(0).getBounds()
        center = bounds.getCenter()
        radius = bounds.getRadius() * 1.1
 
        # Create a collision sphere and name it something understandable.
        collSphereStr = 'CollisionHull' + str(self.collCount) + "_" + obj.getName()
        self.collCount += 1
        cNode = CollisionNode(collSphereStr)
        cNode.addSolid(CollisionSphere(center, radius))
 
        cNodepath = obj.attachNewNode(cNode)
        if show:
            cNodepath.show()
 
        # Return a tuple with the collision node and its corrsponding string so
        # that the bitmask can be set.
        return (cNodepath, collSphereStr)
예제 #24
0
class Starfox(ShowBase):
    def __init__(self):
        super().__init__(self)
        self.scene = self.loader.loadModel("./models/world.egg")
        self.scene.reparentTo(self.render)

        base.cTrav = CollisionTraverser()
        self.collisionHandlerEvent = CollisionHandlerEvent()
        base.enableParticles()

        #base.messenger.toggleVerbose()

        #self.collisionHandlerEvent.addInPattern('from-%in')
        self.collisionHandlerEvent.addInPattern('into-%in')
        self.collisionHandlerEvent.addOutPattern('outof-%in')

        self.player = self.scene.find("player")
        self.enemy = self.scene.find("enemy1")
        self.player.setPythonTag("ObjectController",
                                 Player(self.player, collisionMask=0x4))
        self.building_enemy = self.scene.find("building_enemy")

        #self.player.setPos(self.scene, 0,0,5)
        self.camera.setPos(self.render, 0, -50, 100)
        self.taskMgr.add(self.update, "update")

        self.accept('into-collision_enemy', self.crash)
        self.accept('into-collision_player', self.crash)
        self.accept('into-collision_plane', self.crash)

        base.cTrav.addCollider(self.scene.find("player/collision**"),
                               self.collisionHandlerEvent)
        base.cTrav.addCollider(self.scene.find("enemy1/collision**"),
                               self.collisionHandlerEvent)
        base.cTrav.addCollider(self.scene.find("basePlane/collision**"),
                               self.collisionHandlerEvent)

        #base.cTrav.showCollisions(self.render)

        InputManager.initWith(self, [
            InputManager.arrowUp, InputManager.arrowDown,
            InputManager.arrowRight, InputManager.arrowLeft, InputManager.keyS,
            InputManager.keyA, InputManager.space, InputManager.keyX,
            InputManager.keyV
        ])

        self.rails = self.scene.attachNewNode("rails")
        self.rails.setPos(self.scene, 0, 0, 0)
        self.rails_y = 0
        self.player.reparentTo(self.rails)

        self.player.setPos(self.rails, 0, 20, 0)

        #self.createStaticEnemy(self.building_enemy ,  -100 ,500, 0 )
        self.createStaticEnemy(self.building_enemy, 200, 850, 0)
        self.createStaticEnemy(self.building_enemy, -100, 1000, 0)
        self.createDynamicEnemy(self.enemy, -80, 500, 20, -200, 500, 20)

    def createDynamicEnemy(self, original, ox, oy, oz, tx=0, ty=0, tz=0):
        """
        de = DynamicEnemy( Vec3(ox,oy,oz), self.scene, original, self.player,
                base.cTrav,
                self.collisionHandlerEvent,
                vel=5,
                distanceToAttack = 80
            )
        de.setTargetPos( Vec3(tx,ty,tz) )
        """
        de = DynamicEnemy(Vec3(ox, oy, oz),
                          self.scene,
                          original,
                          self.player,
                          base.cTrav,
                          self.collisionHandlerEvent,
                          type=ENEMY_TYPE.CHASER,
                          vel=35,
                          distanceToAttack=2000,
                          collisionMask=0x3)

    def createStaticEnemy(self, original, x, y, z):
        be = original.copyTo(self.scene)
        be.setPos(self.scene, x, y, z)
        base.cTrav.addCollider(be.find("**collision**"),
                               self.collisionHandlerEvent)
        be.find("**collision*").node().setIntoCollideMask(0x3)
        be.find("**collision*").node().setFromCollideMask(0x3)

    def crash(self, evt):
        #a = 2
        objectInto = evt.getIntoNodePath().node().getParent(0).getPythonTag(
            "ObjectController")
        objectFrom = evt.getFromNodePath().node().getParent(0).getPythonTag(
            "ObjectController")

        if (objectInto != None):
            objectInto.crash(objectFrom)

        if (objectFrom != None):
            objectFrom.crash(objectInto)

        print(f"{objectInto} {objectFrom}")

    def update(self, task):
        extraX, extraZ = self.player.getPythonTag("ObjectController").update(
            self.rails, globalClock.getDt())
        self.rails.setPos(self.scene, Path.getXOfY(self.rails_y), self.rails_y,
                          20)
        #self.camera.lookAt(self.player)
        self.camera.setHpr(Path.getHeading(self.rails_y), 0, 0)
        self.rails.setHpr(Path.getHeading(self.rails_y), 0, 0)
        self.camera.setPos(self.rails, extraX, -10, extraZ)
        self.rails_y = self.rails_y + 20 * globalClock.getDt()

        if self.player.getPythonTag("ObjectController").getShoot():
            v = self.render.getRelativeVector(self.rails, Vec3(0, 1, 0))
            b = Bullet(self.render,
                       self.player.getPos(self.render),
                       self.enemy,
                       base.cTrav,
                       self.collisionHandlerEvent,
                       v,
                       collisionMask=0x3)

        bullets = self.render.findAllMatches("bullet")

        for i in bullets:
            b = i.getPythonTag('ObjectController')
            b.update(globalClock.getDt())

        enemies = self.scene.findAllMatches("dynamicEnemy")

        for i in enemies:
            e = i.getPythonTag('ObjectController')
            s = e.update(globalClock.getDt(), self.rails)
            if (s):
                dir = self.player.getPos(self.render) - i.getPos(self.render)
                dir.normalize()
                b = Bullet(self.render,
                           i.getPos(self.render),
                           self.enemy,
                           base.cTrav,
                           self.collisionHandlerEvent,
                           dir,
                           collisionMask=0xC)

        return Task.cont
class DonkeyKong(ShowBase):
    def __init__(self):
        super().__init__(self)

        self.playerLost = False
        self.playerWon = False

        self.scene = self.loader.loadModel('models/DKSet')
        self.scene.reparentTo(self.render)

        self.arcadeTexture = self.loader.loadTexture('models/dk-arcade.png')
        self.scene.setTexture(self.arcadeTexture)
        self.scene.setTransparency(1)

        self.blockTexture = self.loader.loadTexture('models/block.png')
        self.stairsTexture = self.loader.loadTexture('models/stairs.png')
        self.taskMgr.add(self.setup, "setup")
        self.taskMgr.add(self.update, "update")
        self.jumpAvailable = False
        self.baseTime = 0
        self.v0 = 0
        self.gravity = -.5
        self.stairsAvailable = False
        self.lastPlayerValidZ = 0
        self.hammerTime = False
        self.dkTimer = 5
        self.lifeCounter = 3

    def pressUp(self):
        print("up")
        self.input["up"] = not self.input["up"]

    def pressDown(self):
        print("down")
        self.input["down"] = not self.input["down"]

    def pressLeft(self):
        print("left")
        self.input["left"] = not self.input["left"]

    def pressRight(self):
        print("right")
        self.input["right"] = not self.input["right"]

    def pressSpace(self):
        print("space")
        self.input["space"] = not self.input["space"]

    def hammerFrame1(self):
        self.hammerDown.show()
        self.hammerUp.hide()

    def hammerFrame2(self):
        self.hammerDown.hide()
        self.hammerUp.show()

    def setup(self, task):
        lens = OrthographicLens()
        lens.setFilmSize(25, 20)
        base.camNode.setLens(lens)

        self.player = self.scene.attachNewNode("Player")

        self.scene.find("root/barrel").setPos(0, 100, 0)

        self.scene.find("root/walls").hide()

        self.scene.find("root/rightWall").hide()

        self.lifes = [
            self.scene.attachNewNode("life1"),
            self.scene.attachNewNode("life2"),
            self.scene.attachNewNode("life3"),
        ]
        # init mario gfx stuff
        self.marioGfx = self.scene.find('root/mario')
        self.marioGfx.instanceTo(self.lifes[0])
        self.marioGfx.instanceTo(self.lifes[1])
        self.marioGfx.instanceTo(self.lifes[2])
        self.lifes[0].setPos(-9, 0, 7.5)
        self.lifes[1].setPos(-10, 0, 7.5)
        self.lifes[2].setPos(-11, 0, 7.5)

        self.marioGfx.reparentTo(self.player)
        self.marioGfx.setTwoSided(True)
        self.hammerDown = self.scene.find('root/hammerdowm')
        self.hammerDown.reparentTo(self.marioGfx)
        self.hammerDown.setPos(1, 0, 0)
        self.hammerUp = self.scene.find('root/hammerup')
        self.hammerUp.reparentTo(self.marioGfx)
        self.hammerUp.setPos(0, 0, 1)
        self.hammerDown.hide()
        self.hammerUp.hide()

        frame1 = Func(self.hammerFrame1)
        frame2 = Func(self.hammerFrame2)
        delay = Wait(0.1)
        self.hammerSequence = Sequence(frame1, delay, frame2, delay)
        #sequence.loop()
        #sequence.start()
        #sequence.finish()

        #input setup
        self.accept("raw-arrow_up", self.pressUp)
        self.accept("raw-arrow_down", self.pressDown)
        self.accept("raw-arrow_left", self.pressLeft)
        self.accept("raw-arrow_right", self.pressRight)
        self.accept("raw-space", self.pressSpace)

        self.accept("raw-arrow_up-up", self.pressUp)
        self.accept("raw-arrow_down-up", self.pressDown)
        self.accept("raw-arrow_left-up", self.pressLeft)
        self.accept("raw-arrow_right-up", self.pressRight)
        self.accept("raw-space-up", self.pressSpace)
        self.input = {
            'left': False,
            'right': False,
            'up': False,
            'down': False,
            'space': False
        }

        # collision handling
        base.cTrav = CollisionTraverser()
        self.collisionHandlerEvent = CollisionHandlerEvent()
        self.collisionHandlerEvent.addInPattern('into-%in')
        self.collisionHandlerEvent.addOutPattern('outof-%in')

        ray = CollisionSegment(0, 0, 0, 0, 0, -.6)
        cNodePath = self.player.attachNewNode(CollisionNode('marioRay'))
        cNodePath.node().addSolid(ray)
        cNodePath.node().setIntoCollideMask(0x3)
        cNodePath.node().setFromCollideMask(0x3)
        cNodePath.show()
        base.cTrav.addCollider(cNodePath, self.collisionHandlerEvent)

        self.donkeykonggfx = self.scene.find(f'root/donkeykong')
        self.donkeykong = self.createSquareCollider(8.7, 5, 1, 1, 'donkeykong',
                                                    'dkHitbox', 'DK',
                                                    self.reachedDk,
                                                    self.exitDk,
                                                    self.arcadeTexture, 0x2)

        self.floor1 = self.createSquareCollider(-1.8, -5.5, 9.3, .5, 'floor0',
                                                'floor1Hitbox', 'Floor1',
                                                self.enableJump,
                                                self.disableJump,
                                                self.blockTexture, 0x01)
        self.floor2 = self.createSquareCollider(2.08, -2.5, 8.0, .5, 'floor1',
                                                'floor2Hitbox', 'Floor2',
                                                self.enableJump,
                                                self.disableJump,
                                                self.blockTexture, 0x01)
        self.floor3_1 = self.createSquareCollider(3.6, 0.5, 3.8, .5, 'floor2',
                                                  'floor3_1Hitbox', 'Floor3_1',
                                                  self.enableJump,
                                                  self.disableJump,
                                                  self.blockTexture, 0x01)
        self.floor3_2 = self.createSquareCollider(-6.3, 0.5, 5, .5, 'pCube4',
                                                  'floor3_2Hitbox', 'Floor3_2',
                                                  self.enableJump,
                                                  self.disableJump,
                                                  self.blockTexture, 0x01)
        self.floor4 = self.createSquareCollider(1.8, 3.5, 8, .5, 'floors',
                                                'floor4Hitbox', 'Floor4',
                                                self.enableJump,
                                                self.disableJump,
                                                self.blockTexture, 0x01)

        self.hammer = self.createSquareCollider(6, 1.5, .5, .5, 'hammer',
                                                'hammerHitbox', 'hammer',
                                                self.enableHammer,
                                                self.disableHammer,
                                                self.arcadeTexture, 0x02)

        self.topstair = self.createSquareCollider(
            -6.8, 3.5, 0.5, 2.5, 'topstair', 'topstairHitbox', 'TopStair',
            self.enableStairs, self.disableStairs, self.stairsTexture, 0x02)
        self.middlestair = self.createSquareCollider(
            -0.86, 0.1, 0.5, 2.5, 'middlestair', 'middlestairHitbox',
            'MiddleStair', self.enableStairs, self.disableStairs,
            self.stairsTexture, 0x02)
        self.bottomstair = self.createSquareCollider(
            -6.8, -2.5, 0.5, 2.5, 'bottomstair', 'bottomstairHitbox',
            'BottomStair', self.enableStairs, self.disableStairs,
            self.stairsTexture, 0x02)

        self.leftWall = self.invisibleSquareCollider(-12.5, 0, 1, 10,
                                                     "leftWallHitbox",
                                                     "leftWall", 0x1)
        self.rightWall = self.invisibleSquareCollider(11.3, 0, 1, 20,
                                                      "rightWallHitbox",
                                                      "rightWall", 0x1)

        self.barrelDestroyer = self.invisibleSquareCollider(
            -0.5, -10, 10.5, 1, "barrelDestroyHitBox", "barrelDestroyer", 0x1)
        self.barrelBridge = self.invisibleSquareCollider(
            -0.4, 0.5, 2, 0.5, "barrelBridgeHitBox", "barrelBridge", 0x4)
        base.enableParticles()
        self.physicsCollisionPusher = PhysicsCollisionHandler()
        gravity = ForceNode("world-forces")
        gravityP = render.attachNewNode(gravity)
        gravityForce = LinearVectorForce(0, 0, -9.81)
        gravity.addForce(gravityForce)
        base.physicsMgr.addLinearForce(gravityForce)
        self.accept("into-barrelCollider", self.barrelCrash)

        #self.accept("raw-a", self.throwBarrel)

        #base.cTrav.showCollisions(self.render)

        self.barrels_frames = []
        self.barrels_frames.append(0)
        self.barrels_frames.append(0.410573 - 0.375774)
        self.barrels_frames.append(0.444913 - 0.375774)
        self.barrels_frames.append(0.479941 - 0.375774)

        self.createDKSequence()
        self.player.setPos(3, 0, -3)
        return Task.done

    def changeDkFrame(self, dk, new_u, new_v):
        dk.setTexOffset(TextureStage.getDefault(), new_u, new_v)

    def createDKSequence(self):
        #self.donkeykonggfx
        f1 = Func(self.changeDkFrame, self.donkeykonggfx, 0.140867 - 0.0446603,
                  0)
        f2 = Func(self.changeDkFrame, self.donkeykonggfx,
                  0.0431023 - 0.0446603, 0.806672 - 0.703844)
        f3 = Func(self.changeDkFrame, self.donkeykonggfx, 0, 0)
        th = Func(self.throwBarrel)
        d = Wait(0.2)

        self.dk_sequence = Sequence(f1, d, f2, d, f3, th, d, f1)

    def reachedDk(self, evt):
        if (self.hammerTime):
            self.playerWon = True
        else:
            self.playerLost = True
        print("dk entered")

    def exitDk(self, evt):
        print("dk exit")

    def enableHammer(self, evt):
        self.hammerTime = True
        self.hammerSequence.loop()
        self.scene.node().removeChild(
            evt.getIntoNodePath().node().getParent(0))

    def disableHammer(self, evt):
        pass

    def barrelCrash(self, evt):
        physicsBarrel = evt.getIntoNodePath().node().getParent(0).getParent(0)
        other = evt.getFromNodePath().node().getParent(0)

        if (other.name == "leftWall" or other.name == "rightWall"):
            forceNode = physicsBarrel.getChildren()[1]
            force = forceNode.getForce(0)
            force.setVector(force.getLocalVector().x * -1, 0, 0)
            forceNode.clear()
            forceNode.addForce(force)

        if other.name == "barrelDestroyer":
            self.scene.node().removeChild(physicsBarrel.getParent(0))

        if other.name == "Player":
            if (self.hammerTime):
                self.scene.node().removeChild(physicsBarrel.getParent(0))
            else:
                self.lifeCounter = self.lifeCounter - 1
                if (self.lifeCounter < 0):
                    self.playerLost = True
                else:
                    self.lifes[self.lifeCounter].hide()

    def throwBarrel(self):
        barrelNode = self.scene.attachNewNode("PhysicalBarrel")
        physicsBarrel = ActorNode("physics_barrel")
        physicsBarrel.getPhysicsObject().setMass(0.01)

        barrel = barrelNode.attachNewNode(physicsBarrel)
        base.physicsMgr.attachPhysicalNode(physicsBarrel)

        visualBarrel = barrel.attachNewNode("BarrelCopy")
        originalBarrel = self.scene.find("root/barrel")
        originalBarrel.instanceTo(visualBarrel)
        visualBarrel.setPos(0, -100, 0)

        sphere = CollisionSphere(0.16, 100, 0, 0.5)
        cNodePath = visualBarrel.attachNewNode(CollisionNode("barrelCollider"))
        cNodePath.node().addSolid(sphere)
        cNodePath.node().setFromCollideMask(0x05)
        cNodePath.node().setIntoCollideMask(0x05)
        #cNodePath.show()

        self.physicsCollisionPusher.addCollider(cNodePath, barrel)
        base.cTrav.addCollider(cNodePath, self.physicsCollisionPusher)

        barrelForceNode = ForceNode("barrelForce")
        barrel.attachNewNode(barrelForceNode)
        barrelForce = LinearVectorForce(-8, 0, 0, 1, False)
        barrelForceNode.addForce(barrelForce)
        physicsBarrel.getPhysical(0).addLinearForce(barrelForce)
        barrelNode.setPos(self.scene, 7, 0, 4.5)

        dataNode = AuxNode("sequenceData")
        seq = self.createBarrelSequence(visualBarrel, physicsBarrel, dataNode)
        dataNode.setSequence(seq)

        barrelNode.attachNewNode(dataNode)

    def createBarrelSequence(self, visual, physics, dataNode):
        def updateBarrel():
            vel = physics.getPhysicsObject().getVelocity()
            frame = dataNode.frame

            if (vel.x > 0):
                frame = (frame + 1) % 4
                #vel.x = 5
            if (vel.x < 0):
                frame = (frame - 1) % 4
                #vel.x = -5
            dataNode.frame = frame

            physics.getPhysicsObject().setVelocity(vel)
            visualFrame = self.barrels_frames[frame]
            visual.setTexOffset(TextureStage.getDefault(), visualFrame, 0.0)

        f1 = Func(updateBarrel)
        d = Wait(0.1)

        seq = Sequence(f1, d)
        seq.loop()
        return seq

    def createSquareCollider(self, px, pz, w, h, modelName, collisionNodeName,
                             nodeName, enableFunction, disableFunction,
                             texture, mask):
        obj = self.scene.attachNewNode(nodeName)
        hitbox = CollisionBox(Point3(0, 0, 0), w, 5, h)
        cNodePath = obj.attachNewNode(CollisionNode(collisionNodeName))
        cNodePath.node().addSolid(hitbox)
        cNodePath.node().setIntoCollideMask(mask)
        cNodePath.node().setFromCollideMask(mask)
        #cNodePath.show()
        base.cTrav.addCollider(cNodePath, self.collisionHandlerEvent)

        self.scene.find(f'root/{modelName}').reparentTo(obj)
        obj.setPos(px, 0, pz)
        obj.setTexture(texture)

        self.accept(f'into-{collisionNodeName}', enableFunction)
        self.accept(f'outof-{collisionNodeName}', disableFunction)
        return obj

    def invisibleSquareCollider(self, px, pz, w, h, collisionNodeName,
                                nodeName, mask):
        obj = self.scene.attachNewNode(nodeName)
        hitbox = CollisionBox(Point3(0, 0, 0), w, 5, h)
        cNodePath = obj.attachNewNode(CollisionNode(collisionNodeName))
        cNodePath.node().addSolid(hitbox)
        cNodePath.node().setIntoCollideMask(mask)
        cNodePath.node().setFromCollideMask(mask)
        #cNodePath.show()
        base.cTrav.addCollider(cNodePath, self.collisionHandlerEvent)
        obj.setPos(px, 0, pz)

    def enableJump(self, evt):
        self.lastPlayerValidZ = evt.getIntoNodePath().node().getParent(
            0).getTransform().getPos().z + 1
        self.jumpAvailable = True
        print("enable jump")

    def disableJump(self, evt):
        print(evt.getIntoNodePath().node().getParent(0))
        self.jumpAvailable = False
        print("disable jump")

    def enableStairs(self, evt):

        self.stairsAvailable = True
        print("enable stairs")

    def disableStairs(self, evt):
        self.stairsAvailable = False
        print("disable stairs")

    def applyMove(self):
        mv = Vec3(0, 0, 0)
        p = self.player.getPos()

        if (self.input["left"]):
            self.marioGfx.setSx(self.player, 1)
            mv.x = 0.1
        if (self.input["right"]):
            self.marioGfx.setSx(self.player, -1)
            mv.x = -0.1

        if (self.jumpAvailable):
            mv.z = self.v0 + self.baseTime * self.gravity
            if (not self.stairsAvailable):
                p.z = self.lastPlayerValidZ
            if (mv.z < 0):
                self.v0 = 0
                self.baseTime = 0
                mv.z = 0

        if (self.input["space"] and self.jumpAvailable):
            self.baseTime = 0
            self.v0 = .2
            mv.z = self.v0 + self.baseTime * self.gravity

        if (not self.jumpAvailable and not self.stairsAvailable):
            self.baseTime = self.baseTime + globalClock.getDt()
            mv.z = self.v0 + self.baseTime * self.gravity

        if (self.stairsAvailable):
            self.baseTime = 0
            self.v0 = 0
            if (self.input["up"]):
                mv.z = mv.z + 0.1
            if (self.input["down"] and not self.jumpAvailable):
                mv.z = mv.z - 0.1
        p.x = p.x + mv.x
        p.z = p.z + mv.z
        self.player.setPos(p)

    def update(self, task):
        self.camera.setPos(0, 35, 0)
        self.camera.lookAt(self.scene)

        self.dkTimer = self.dkTimer + globalClock.getDt()

        if (self.dkTimer > 10):
            self.dk_sequence.start()
            self.dkTimer = 0

        if ((self.playerLost or self.playerWon)):
            if (self.playerLost):
                text = DirectLabel(text="Perdiste!!!!", text_scale=(0.5, 0.5))
            if (self.playerWon):
                text = DirectLabel(text="Ganastesss!", text_scale=(0.5, 0.5))
            return Task.done

        self.applyMove()

        return Task.cont
예제 #26
0
class MHBProjectile(DirectObject):
    
    #Property stuff
    creaTime = time.clock()
    dur = .5
    vec = 0
    delta = .15
    prevtime = 0
    flag = False

    #defining the thing fired by whatever gun we have
    def __init__(self, camera, look, id, model):
        self.id = id
        #nodepath of the projectile, give it a trajectory
        self.projectileNode = NodePath('projectile'+str(id))
        self.projectileNode.reparentTo(render)
        
        #by passing the camera node form the camMov object, all projectiles are spawned 5 units in front of the camera
        self.projectileNode.setHpr(look, 0, 0, 0)
        self.projectileNode.setPos(camera,0,3, 3)
        
        #fix z position to line up with gun
        self.projectileNode.setScale(.1)
        projectileModel = loader.loadModel("./resources/cubeShot.egg")
        projectileModel.setColor(255, 0, 0)
        projectileModel.reparentTo(self.projectileNode)
    	
        #must calculate unit vector based on direction
        dir = render.getRelativeVector(look, Vec3(0, 1, 0))
    	
        #speed up or slow down projectiles here
        dir = dir*10
        self.vec = dir

        #Balance vectors when magnitude in direction is low
        if self.vec.x < 2:
            self.vec.x += random.randint(-1,1)
        if self.vec.z < 2:
            self.vec.z += random.randint(-1,1)
        if self.vec.y < 2: 
            self.vec.y += random.randint(-1,1)
        
        #Random vector displacements
        self.vec.x *= random.uniform(.5,1)
        self.vec.y *= random.uniform(.5,1)
        self.vec.z *= random.uniform(.5,1)
        
        
        #base.cTrav = CollisionTraverser()
        cs = CollisionSphere(0, 0, 0, 2.5)
        self.cnodepath = self.projectileNode.attachNewNode(CollisionNode('projNode'))
        self.cnodepath.node().addSolid(cs)
        self.collHand = CollisionHandlerEvent()

        self.cnodepath.setTag('tag', str(self.cnodepath))
        self.collHand.addInPattern('%(tag)ix-into'+str(id))
        self.collHand.addOutPattern('outof')
        #cTrav has the distinction of global colider handler
        base.cTrav.addCollider(self.cnodepath, self.collHand) 
        self.acceptOnce(self.cnodepath.getTag('self')+'-into'+str(id), self.hit)
	    #deal with colliding or special effects here.
	    #wanted projectiles to be short lived
	    # so i will make them delete themselves after impact or time expired
        # writing a task that will rek the projectiles at the end of time
        self.damage = 1.1

    def moveTask(self, task):
        
        #curtime = time.clock()
        #self.delta = curtime-self.prevtime
        
        if self.flag:
            self.ignore(self.cnodepath.getTag('self')+'-into'+str(self.id))
            return task.done
        
        velx = self.vec.x*self.delta
        vely = self.vec.y*self.delta
        velz = self.vec.z*self.delta
        x = self.projectileNode.getX()
        y = self.projectileNode.getY()
        z = self.projectileNode.getZ()
        self.projectileNode.setPos(x+velx, y+vely, z+velz)
        #prevtime = time.clock()
            
        
        self.cnodepath.setTag('tag', str(self))
        if task.time < self.dur:
        
            return task.cont
        else:
            
            self.flag = True
            return task.done
      
    def hit(self, collEntry):
        # throw out a custom message for what hit
        if collEntry.getIntoNodePath().getName() != 'projNode':
            
            temp = collEntry.getIntoNodePath().getName()
            messenger.send(temp, [self.damage]) 
            #remove the impacting projectile
            collEntry.getFromNodePath().getParent().getParent().removeNode()
            self.flag =  True
예제 #27
0
class DKGame(ShowBase):
    def __init__(self):
        super().__init__(self)
        self.t = 1
        self.loadScenery()
        self.mario = None
        #base.messenger.toggleVerbose()
        self.taskMgr.add(self.setup, "setup")
        self.taskMgr.add(self.update, "update")

        self.accept("raw-arrow_right" , self.pressRight)
        self.accept("raw-arrow_right-up" , self.stopRight)
        self.accept("raw-arrow_left" , self.pressLeft)
        self.accept("raw-arrow_left-up" , self.stopLeft)

        self.accept("raw-arrow_up" , self.pressUp)
        self.accept("raw-arrow_up-up" , self.stopUp)

        self.accept("raw-space" , self.pressSpace)
        self.accept("raw-space-up" , self.stopSpace)


        self.canClimb = False
        self.isClimbing = False
        #NUEVA!
        self.isGrounded = True
        self.canJump = True
        self.jumpTime = 0
        self.vyi = 0
        self.floorValidPosition = -4.5

        self.barrelTimer = 0
        self.lifes = 3

        self.marioInitialPos = None
        self.posNotInitialized = True
        self.hammer = False
        self.barrels_frames = []
        self.barrels_frames.append(0)
        self.barrels_frames.append( 0.410573 - 0.375774)
        self.barrels_frames.append( 0.444913 - 0.375774)
        self.barrels_frames.append( 0.479941 - 0.375774)

        self.dk_barrel_sequence = self.createDKBarrelSequence()
        self.hammer_sequence = self.createMarioHammerSequence()
        self.input = {
        "left":False,
        "right":False,
        "space":False,
        "up":False
        }


    def showHammerFrame(self, frame):
        if( frame == 1):
            self.marioRealGraphic.find("hammerup").show()
            self.marioRealGraphic.find("hammerdowm").hide()
        if( frame == 2):
            self.marioRealGraphic.find("hammerdowm").show()
            self.marioRealGraphic.find("hammerup").hide()


    def createMarioHammerSequence(self):
        f1 = Func( self.showHammerFrame , 1  )
        f2 = Func( self.showHammerFrame , 2 )
        delay = Wait(0.1)

        mySequence = Sequence(f1, delay,f2, delay)
        return mySequence


    def changeDKFrame(self, frame):
        dk = self.scene.find("hammer1") #remember that the name is wrong here
        if( frame == 1):
            dk.setTexOffset(TextureStage.getDefault() , 0.140867 - 0.0446603 ,0.0 )
        if( frame == 2):
            dk.setTexOffset(TextureStage.getDefault() , 0.0431023 - 0.0446603 ,  0.806672 - 0.703844 )
        if( frame == 3):
            dk.setTexOffset(TextureStage.getDefault() , 0 ,0.0 )

        """
        frames
        2) 0.140867 0.703844

        1) 0.0431023 0.806672 ;

         throw
        0 0.0446603 0.703065
        """

    def createDKBarrelSequence(self):
        func1 = Func(self.changeDKFrame,1)
        func2 = Func(self.changeDKFrame,2)
        func3 = Func(self.changeDKFrame,3)
        func4 = Func(self.createBarrel)
        delay = Wait(0.5)
        mySequence = Sequence(func1, delay,func2, delay, func3, func4, delay, func1)
        mySequence.loop()
        return mySequence

    def loadScenery(self):
        self.scene = self.loader.loadModel("models/DKSetTextured") # only for non animated objects
        myTexture = loader.loadTexture("models/dk-arcade.png")
        self.scene.setTexture(myTexture)
        self.scene.setTransparency(1)
        self.scene.reparentTo(self.render)

    def setup(self,task):
        lens = OrthographicLens()
        lens.setFilmSize(21.8,18)  # Or whatever is appropriate for your scene
        #lens.setFilmSize(142,136)  # Or whatever is appropriate for your scene

        base.camNode.setLens(lens)

        node = self.scene.find("root/camera1")
        node.removeNode()
        self.camera.setPos( 0,30,0 )
        self.camera.lookAt(self.scene)


        self.mario = self.render.attachNewNode("MarioContainer")
        self.mario.setPos(self.scene, 0,0,0)
        self.marioGraphic = self.mario.attachNewNode("MarioGraphic")
        self.marioGraphic.setPos(self.mario, 0,0,0)
        self.scene.find("root/mario").reparentTo(self.marioGraphic)

        myTexture = loader.loadTexture("models/dk-arcade.png")
        self.marioRealGraphic = self.marioGraphic.find("mario")
        self.marioRealGraphic.setPos(self.marioGraphic, -6.7, 1, 4.5 )
        self.marioRealGraphic.setTexture(myTexture)
        self.marioRealGraphic.setTwoSided(True)
        self.marioRealGraphic.setTransparency(1)


        self.scene.find("root/hammerup").reparentTo(self.marioRealGraphic)
        self.scene.find("root/hammerdowm").reparentTo(self.marioRealGraphic)
        self.marioRealGraphic.find("hammerup").hide()
        self.marioRealGraphic.find("hammerdowm").hide()

        self.scene.find("root/bottomstair").reparentTo(self.scene)
        self.scene.find("root/floor0").reparentTo(self.scene)
        self.scene.find("root/floor1").reparentTo(self.scene)


        self.scene.find("root/middlestair").reparentTo(self.scene)
        self.scene.find("root/topstair").reparentTo(self.scene)

        self.scene.find("root/floor2").reparentTo(self.scene)
        self.scene.find("root/pCube4").reparentTo(self.scene)
        self.scene.find("root/floors").reparentTo(self.scene)
        self.scene.find("root/barrel").reparentTo(self.scene)

        self.scene.find("root/walls").reparentTo(self.scene)
        self.scene.find("root/rightWall").reparentTo(self.scene)

        self.scene.find("root/MainGroup").reparentTo(self.scene)
        self.scene.find("root/hammer1").reparentTo(self.scene)

        self.barrel = self.scene.find("barrel")
        self.barrel.setPos(self.scene, 0,0,20)

        myTexture = loader.loadTexture("models/block.png")
        self.scene.find("floor0").setTexture(myTexture)
        self.scene.find("floor1").setTexture(myTexture)
        self.scene.find("floor2").setTexture(myTexture)
        self.scene.find("floors").setTexture(myTexture)
        self.scene.find("pCube4").setTexture(myTexture)

        self.scene.find("floor0").setTransparency(1)
        self.scene.find("floor1").setTransparency(1)
        self.scene.find("floor2").setTransparency(1)
        self.scene.find("floors").setTransparency(1)
        self.scene.find("pCube4").setTransparency(1)

        myTexture = loader.loadTexture("models/stairs.png")
        self.scene.find("bottomstair").setTexture(myTexture)
        self.scene.find("middlestair").setTexture(myTexture)
        self.scene.find("topstair").setTexture(myTexture)

        self.scene.find("bottomstair").setTransparency(1)
        self.scene.find("middlestair").setTransparency(1)
        self.scene.find("topstair").setTransparency(1)

        base.setBackgroundColor(0,0,0)

        self.setupCollision()

        base.enableParticles()
        gravityFN=ForceNode('world-forces')
        gravityFNP=render.attachNewNode(gravityFN)
        gravityForce=LinearVectorForce(0,0,-9.81) #gravity acceleration
        gravityFN.addForce(gravityForce)
        base.physicsMgr.addLinearForce(gravityForce)


        # create dk graphic barrel sequence


        return Task.done


    def barrelGraphicUpdate(self, visual, physics, data):
        def update():
            vel = physics.getPhysicsObject().getVelocity()
            prevFrame = data.node().getPythonTag("subclass").frame
            if( vel.x < 0):
                data.node().getPythonTag("subclass").frame = (prevFrame - 1)%4
            else:
                data.node().getPythonTag("subclass").frame =  (prevFrame + 1)%4

            visual.setTexOffset(TextureStage.getDefault() , self.barrels_frames[prevFrame] ,0.0 )

        return update

    def createBarrelGraphicSequence(self, visual, physics, data):

        funcInterval = FunctionInterval(self.barrelGraphicUpdate(visual, physics, data), name = "BarrelGraphicUpdate")
        delay = Wait(0.1)
        mySequence = Sequence(funcInterval, delay)
        mySequence.loop()
        return mySequence

    def createBarrel(self):

        barrelNode = NodePath("PhysicalBarrel")
        barrelNode.reparentTo(self.scene)
        barrelNode.setPos(self.scene, 0,0,0)
        physicsBarrel = ActorNode("physics_barrel")
        physicsBarrel.getPhysicsObject().setMass(0.01) #in what units? (69 kindda 3 lbs)
        barrel = barrelNode.attachNewNode(physicsBarrel)
        base.physicsMgr.attachPhysicalNode(physicsBarrel)

        barrel.setPos(barrelNode, 0,0,0)

        visual_barrel = self.scene.attachNewNode("BarrelCopy")
        originalBarrel = self.scene.find("barrel")
        originalBarrel.instanceTo(visual_barrel)
        visual_barrel.reparentTo(barrel)
        visual_barrel.setPos(self.scene, -6.5,0,-24.5 )

        dataNode = barrelNode.attachNewNode(AuxData("Sequence",None))
        seq = self.createBarrelGraphicSequence(visual_barrel, physicsBarrel, dataNode)
        dataNode.node().getPythonTag("subclass").sequence = seq

        #sphere =  CollisionSphere(6.6,0,4.78, 0.5)
        sphere =  CollisionSphere(6.6,0,24.7, 0.5)
        cnodePath = visual_barrel.attachNewNode(CollisionNode('barrelCollider'))
        cnodePath.node().addSolid(sphere)
        cnodePath.node().setFromCollideMask(0xD) # crash with default and mario body and walls
        cnodePath.node().setIntoCollideMask(0xD) # crash with default and mario body and walls
        self.showCollision(cnodePath)
        #cnodePath.show()
        self.physicsCollisionPusher.addCollider(cnodePath,barrel)
        base.cTrav.addCollider(cnodePath, self.physicsCollisionPusher)

        barrelForceNode = ForceNode('barrelForce')
        barrel.attachNewNode(barrelForceNode)
        barrelForce = LinearVectorForce(-7,0,0, 1, False)
        # barrelForce.setMassDependent(0)
        barrelForceNode.addForce(barrelForce)
        physicsBarrel.getPhysical(0).addLinearForce(barrelForce)
        # starting barrel point :D
        barrelNode.setPos(self.scene,6.5,0,4.5)

    def setupBoxCollider(self , node, px, py, pz, w,d,h, nm, colliderEventHandler , fromCollisionMask=0, intoCollisionMask=0  ):

        hitBox = CollisionBox(  Point3(px,py,pz) , w,d,h)
        cnodePath = node.attachNewNode( CollisionNode(nm) )
        cnodePath.node().addSolid(hitBox)
        cnodePath.node().setIntoCollideMask(intoCollisionMask)
        cnodePath.node().setFromCollideMask(fromCollisionMask)
        # cnodePath.show()
        self.showCollision(cnodePath)

        base.cTrav.addCollider(cnodePath, colliderEventHandler)


    def setupCollision(self):
        base.cTrav = CollisionTraverser()
        self.collisionHandlerEvent = CollisionHandlerEvent()
        self.physicsCollisionPusher = PhysicsCollisionHandler()

        self.collisionHandlerEvent.addInPattern('into-%in')
        self.collisionHandlerEvent.addOutPattern('outof-%in')

        # create masks
        defaultCollisionMask =      BitMask32(0b0001) #0x1
        segmentCollisionMask =      BitMask32(0b1000) #0x8
        stairsCollisionMask =       BitMask32(0b0010) #0x2
        marioBodyCollisionMask =    BitMask32(0b0011) #0x3
        collisionWallsForBarrels =  BitMask32(0b0100) #0x4


        # mario segment collider
        #ray =  CollisionSegment(7,0,-4.5, 7,0,-5.1)
        ray =  CollisionSegment(0,0,0, 0,0,-.51)
        cnodePath = self.mario.attachNewNode(CollisionNode('marioRay'))
        cnodePath.node().addSolid(ray)
        cnodePath.node().setFromCollideMask(segmentCollisionMask)
        cnodePath.node().setIntoCollideMask(0)
        self.showCollision(cnodePath)
        base.cTrav.addCollider(cnodePath, self.collisionHandlerEvent)

        #self.setupBoxCollider(self.mario, 7,0,-4.5, 0.5,5,0.5, 'marioHitBox', self.collisionHandlerEvent, marioBodyCollisionMask,marioBodyCollisionMask )
        self.setupBoxCollider(self.mario, 0,0,0, 0.5,5,0.5, 'marioHitBox', self.collisionHandlerEvent, marioBodyCollisionMask,marioBodyCollisionMask )


        stairs1 =  self.scene.find("bottomstair")
        self.setupBoxCollider(stairs1, -6.8,0,-3.0, 0.5,5,2.5, 'stairs1HitBox', self.collisionHandlerEvent, stairsCollisionMask,stairsCollisionMask )

        stairs2 =  self.scene.find("middlestair")
        self.setupBoxCollider(stairs2, -0.86,0, .1, 0.5,5,2.1, 'stairs2HitBox', self.collisionHandlerEvent, stairsCollisionMask,stairsCollisionMask  )

        stairs3 =  self.scene.find("topstair")
        self.setupBoxCollider(stairs3, -6.8,0, 3.1, 0.5,5,2.2, 'stairs3HitBox', self.collisionHandlerEvent, stairsCollisionMask,stairsCollisionMask  )

        hammer =  self.scene.find("MainGroup") # hammer
        self.setupBoxCollider(hammer, 5.5,0, -1.5, 0.5,5,0.5, 'hammer1HitBox', self.collisionHandlerEvent, stairsCollisionMask,stairsCollisionMask  )

        dk =  self.scene.find("hammer1")
        self.setupBoxCollider(dk, 8.7,0, 5, 1,5,1, 'dkHitBox', self.collisionHandlerEvent, stairsCollisionMask,stairsCollisionMask  )

        floor0 =  self.scene.find("floor0")
        self.setupBoxCollider(floor0, -2.5,0,-5.5, 10,5,0.5, 'floor0HitBox', self.collisionHandlerEvent , intoCollisionMask=segmentCollisionMask )

        floor1 =  self.scene.find("floor1")
        self.setupBoxCollider(floor1, 2,0, -2.5, 8.4,5,0.5, 'floor1HitBox', self.collisionHandlerEvent , intoCollisionMask=segmentCollisionMask )
        floor2_1 =  self.scene.find("floor2")
        self.setupBoxCollider(floor2_1, 3.6,0, 0.5, 3.8,5,0.5, 'floor21HitBox', self.collisionHandlerEvent, intoCollisionMask=segmentCollisionMask )
        floor2_2 =  self.scene.find("pCube4")
        self.setupBoxCollider(floor2_2, -6.3,0, 0.5, 5.0 ,5,0.5, 'floor22HitBox', self.collisionHandlerEvent, intoCollisionMask=segmentCollisionMask )
        floor3 =  self.scene.find("floors")
        self.setupBoxCollider(floor3, 1.8,0, 3.5, 8,5,0.5, 'floor3HitBox',  self.collisionHandlerEvent , intoCollisionMask=segmentCollisionMask )

        rightWall = self.scene.find("rightWall")
        self.setupBoxCollider(rightWall, -12,0, 0, 1,5,10, 'rightWallHitBox',  self.collisionHandlerEvent , fromCollisionMask=collisionWallsForBarrels, intoCollisionMask=collisionWallsForBarrels )

        leftWall = self.scene.find("walls")
        self.setupBoxCollider(leftWall, 11.5,0, 0, 1,5,10, 'leftWallHitBox',  self.collisionHandlerEvent , fromCollisionMask=collisionWallsForBarrels, intoCollisionMask=collisionWallsForBarrels )


        barrelFixer = self.scene.attachNewNode("barrelFixer")
        self.setupBoxCollider(barrelFixer, -3,0, 0.505, 10,5,0.5, 'barrelFixerHitBox',  self.collisionHandlerEvent , fromCollisionMask=collisionWallsForBarrels, intoCollisionMask=collisionWallsForBarrels )

        barrelDestroyer = self.scene.attachNewNode("barrelDestroyer")
        self.setupBoxCollider(barrelDestroyer, 0,0, -8, 15,5,0.5, 'barrelDestroyerHitBox',  self.collisionHandlerEvent , fromCollisionMask=collisionWallsForBarrels, intoCollisionMask=collisionWallsForBarrels )


        self.accept('into-stairs1HitBox', self.enableStair)
        self.accept('outof-stairs1HitBox', self.disableStair)
        self.accept('into-stairs2HitBox', self.enableStair)
        self.accept('outof-stairs2HitBox', self.disableStair)
        self.accept('into-stairs3HitBox', self.enableStair)
        self.accept('outof-stairs3HitBox', self.disableStair)
        self.accept('into-hammer1HitBox', self.enableHammer)
        self.accept('into-dkHitBox', self.dkArrived)

        self.accept('into-floor0HitBox', self.enableJump)
        self.accept('outof-floor0HitBox', self.disableJump)
        self.accept('into-floor1HitBox', self.enableJump)
        self.accept('outof-floor1HitBox', self.disableJump)
        self.accept('into-floor21HitBox', self.enableJump)
        self.accept('outof-floor21HitBox', self.disableJump)
        self.accept('into-floor22HitBox', self.enableJump)
        self.accept('outof-floor22HitBox', self.disableJump)
        self.accept('into-floor3HitBox', self.enableJump)
        self.accept('outof-floor3HitBox', self.disableJump)

        self.accept("into-barrelCollider", self.barrelCrash)

        #base.cTrav.showCollisions(self.render)

    def showCollision(self, col):
        #col.show()
        print("Not showing collider")

    def dkArrived(self,evt):
        if(self.hammer):
            self.scene.node().removeChild(evt.getIntoNodePath().node().getParent(0))
            text = DirectLabel(text="You won", text_scale=(0.5,0.5))
        else:
            self.floorValidPosition = -4.5
            self.mario.setPos(self.scene, self.marioInitialPos)
            text = DirectLabel(text="Game Over", text_scale=(0.5,0.5))


    def enableHammer(self, evt):
        print(f"{evt.getIntoNodePath()}{evt.getFromNodePath()}")
        self.scene.node().removeChild(evt.getIntoNodePath().node().getParent(0))
        self.hammer_sequence.loop()
        self.hammer = True

    def changeBarrelDirection(self, evt):
        print(f"Changing barrel direction {evt}")


    def barrelCrash(self,evt):
        barrel = evt.getIntoNodePath().node().getParent(0).getParent(0)
        other = evt.getFromNodePath().node().getParent(0)

        parents = barrel.parents
        # print(f"{other}")

        if other.name=="barrelDestroyer":
            p = parents[0]
            childrens = barrel.getParent(0).getChildren()
            childrens[1].getPythonTag("subclass").sequence.finish()
            self.scene.node().removeChild(p)
            return

        if not (other==self.mario.node() or other.name=="barrelFixer" ) :
            forceNode = barrel.getChildren()[1]
            actualForce = forceNode.getForce(0)
            actualForce.setVector( actualForce.getLocalVector().x*-1, 0 , 0 )
            forceNode.clear()
            forceNode.addForce(actualForce)


        if( other == self.mario.node() ):
            if not self.hammer:
                self.lifes = self.lifes - 1
                self.floorValidPosition = -4.5
                self.mario.setPos(self.scene, self.marioInitialPos)

            p = parents[0]
            childrens = barrel.getParent(0).getChildren()
            childrens[1].getPythonTag("subclass").sequence.finish()
            self.scene.node().removeChild(p)

            if(  self.lifes < 0):
                print("game over dude!!")
                text = DirectLabel(text="Game Over", text_scale=(0.5,0.5))

    def enableStair(self, evt):
        print("crashed mario and stair");
        self.canClimb = True

    def disableStair(self, evt):
        print("exit mario and stair");
        self.canClimb = False

    def enableJump(self, evt):
        self.isGrounded = True
        print("enable jump")
        # fromCollider =  evt.getFrom().getCenter().z - evt.getFrom().getDimensions().z/2

        self.floorValidPosition = evt.getInto().getCenter().z + 1
        print(f"{ evt.getInto().getCenter().z } {self.floorValidPosition} ")

    def disableJump(self, evt):
        print("disable jump")
        self.isGrounded = False

    def pressUp(self):
        print("up enabled")
        self.input["up"] = True;

    def stopUp(self):
        print("up disabled")
        self.input["up"] = False;

    def pressRight(self):
        self.input["right"] = True;

    def stopRight(self):
        self.input["right"] = False;

    def pressLeft(self):
        self.input["left"] = True;

    def stopLeft(self):
        self.input["left"] = False;

    def pressSpace(self):
        self.input["space"] = True;
        #self.camera.setPos( 0,30,0 )
        #self.camera.lookAt(self.scene)

    def stopSpace(self):
        self.input["space"] = False;

    def getAdvance(self):
        if self.input["left"] and self.input["right"]:
            return 0
        if self.input["left"]:
            return -1
        if self.input["right"]:
            return 1
        return 0

    def applyJump(self):
        jz = 0  # jump Y/Z
        vi = 4 # initial velocity
        g = -6 # gravity

        if(self.isGrounded):
            if(self.canJump):
                if(self.input["space"]):
                    self.jumpTime = 0.1
                    self.canJump = False
                    self.vyi = vi
                    jz = self.vyi*self.jumpTime  + 0.5*g*self.jumpTime*self.jumpTime
                    vz = self.vyi + g*self.jumpTime
                else:
                    return 0
            else:
                self.jumpTime = self.jumpTime + globalClock.getDt()
                jz = self.vyi*self.jumpTime  + 0.5*g*self.jumpTime*self.jumpTime
                vz = self.vyi + g*self.jumpTime
                if vz < 0: #finished
                    self.jumpTime = 0
                    self.canJump = True
                    self.vyi = 0
                    jz = 0
        else:
            if(not self.isClimbing):
                self.canJump = False
                self.jumpTime = self.jumpTime + globalClock.getDt()
                jz = self.vyi*self.jumpTime  + 0.5*g*self.jumpTime*self.jumpTime
                vz = self.vyi + g*self.jumpTime

        return jz
    def applyStairs(self, pz):
        if( self.canClimb):
            if(self.input["up"]):
                self.isClimbing = True

        if( self.isClimbing ):
            if( self.input["up"]):
                return pz + 0.1
        if( not self.canClimb):
            self.isClimbing = False

        return pz
    def update(self,task):
        self.camera.setPos( 0,30,0 )
        self.camera.lookAt(self.scene)
        pz = self.applyJump()

        if( self.posNotInitialized):
            self.marioInitialPos = self.mario.getPos()
            self.posNotInitialized = False

        self.barrelTimer = self.barrelTimer + globalClock.getDt()
        if self.barrelTimer > (3 + random()*2):  # fix error! when dk has lost! -> exercise :D
            self.dk_barrel_sequence.start()
            self.barrelTimer = 0

        # self.mario.getPos(self.render).z
        advZ = self.applyStairs(self.floorValidPosition )
        self.floorValidPosition = advZ

        if( self.getAdvance() != 0):
            self.marioGraphic.setSx(self.mario, -self.getAdvance())

        self.mario.setPos(self.render, self.mario.getPos().x + -self.getAdvance()*.1 , 0 , advZ+pz ) # advZ+pz

        return Task.cont
예제 #28
0
class ChargeProjectile(DirectObject):
    
    dur = 2
    delta = .15
    flag = False
    
    def __init__(self, spawn, taregt, id):
        
        self.projectileNode = NodePath('projectile'+str(id))
        self.projectileNode.reparentTo(render)

        self.projectileNode.setPos(spawn,0,-10, 0)
        self.projectileNode.setScale(1.5)
        self.projectileModel = Actor("./resources/sphereShot",{"grow":"./resources/sphereShot-grow"})
        self.projectileModel.setColorScale(200, 0, 255, 100)
        self.projectileModel.reparentTo(self.projectileNode)
        self.projectileNode.setHpr(spawn, 0, 0, 0)


        dir = render.getRelativeVector(spawn, Vec3(0, 1, 0))
        self.vec = dir*-100
        cs = CollisionSphere(0, 0, 0, 2.5)
        cnodepath = self.projectileNode.attachNewNode(CollisionNode('projNode'))
        cnodepath.node().addSolid(cs)
        self.collHand = CollisionHandlerEvent()
        self.collHand.addInPattern('bossProjectileinto'+str(id))
        self.collHand.addOutPattern('outof')
        base.cTrav.addCollider(cnodepath, self.collHand)
        self.acceptOnce('bossProjectileinto'+str(id), self.hit)
        self.damage = 15


    def moveTask(self, task):    
        
        if self.flag:
            return task.done
        
        velx = self.vec.x*self.delta
        vely = self.vec.y*self.delta
        velz = self.vec.z*self.delta
        x = self.projectileNode.getX()
        y = self.projectileNode.getY()
        z = self.projectileNode.getZ()
        self.projectileNode.setPos(x+velx, y+vely, z+velz)

        if task.time < self.dur:
        
            return task.cont
        else:
            
            self.flag = True
            return task.done

    def hit(self, collEntry):
        
        #throw out a custom message for what hit
        if collEntry.getIntoNodePath().getName() != 'projNode':
           
            temp = collEntry.getIntoNodePath().getName()
            print temp
            messenger.send(temp, [self.damage]) 
            
            #remove the impacting projectile
            collEntry.getFromNodePath().getParent().getParent().removeNode()
            self.flag =  True
            del self

    def wait(self, task):

        if task.time > 2.24:
            return task.done
	    
        return task.cont
예제 #29
0
class CogdoFlyingCollisions(GravityWalker):
    wantFloorSphere = 0

    def __init__(self):
        GravityWalker.__init__(self, gravity=0.0)

    def initializeCollisions(self,
                             collisionTraverser,
                             avatarNodePath,
                             avatarRadius=1.4,
                             floorOffset=1.0,
                             reach=1.0):
        self.cHeadSphereNodePath = None
        self.cFloorEventSphereNodePath = None
        self.setupHeadSphere(avatarNodePath)
        self.setupFloorEventSphere(avatarNodePath,
                                   ToontownGlobals.FloorEventBitmask,
                                   avatarRadius)
        GravityWalker.initializeCollisions(self, collisionTraverser,
                                           avatarNodePath, avatarRadius,
                                           floorOffset, reach)
        return

    def setupWallSphere(self, bitmask, avatarRadius):
        self.avatarRadius = avatarRadius
        cSphere = CollisionSphere(0.0, 0.0, self.avatarRadius + 0.75,
                                  self.avatarRadius)
        cSphereNode = CollisionNode('Flyer.cWallSphereNode')
        cSphereNode.addSolid(cSphere)
        cSphereNodePath = self.avatarNodePath.attachNewNode(cSphereNode)
        cSphereNode.setFromCollideMask(bitmask)
        cSphereNode.setIntoCollideMask(BitMask32.allOff())
        if config.GetBool('want-fluid-pusher', 0):
            self.pusher = CollisionHandlerFluidPusher()
        else:
            self.pusher = CollisionHandlerPusher()
        self.pusher.addCollider(cSphereNodePath, self.avatarNodePath)
        self.cWallSphereNodePath = cSphereNodePath

    def setupEventSphere(self, bitmask, avatarRadius):
        self.avatarRadius = avatarRadius
        cSphere = CollisionSphere(0.0, 0.0, self.avatarRadius + 0.75,
                                  self.avatarRadius * 1.04)
        cSphere.setTangible(0)
        cSphereNode = CollisionNode('Flyer.cEventSphereNode')
        cSphereNode.addSolid(cSphere)
        cSphereNodePath = self.avatarNodePath.attachNewNode(cSphereNode)
        cSphereNode.setFromCollideMask(bitmask)
        cSphereNode.setIntoCollideMask(BitMask32.allOff())
        self.event = CollisionHandlerEvent()
        self.event.addInPattern('enter%in')
        self.event.addOutPattern('exit%in')
        self.cEventSphereNodePath = cSphereNodePath

    def setupRay(self, bitmask, floorOffset, reach):
        cRay = CollisionRay(0.0, 0.0, 3.0, 0.0, 0.0, -1.0)
        cRayNode = CollisionNode('Flyer.cRayNode')
        cRayNode.addSolid(cRay)
        self.cRayNodePath = self.avatarNodePath.attachNewNode(cRayNode)
        cRayNode.setFromCollideMask(bitmask)
        cRayNode.setIntoCollideMask(BitMask32.allOff())
        self.lifter = CollisionHandlerGravity()
        self.lifter.setLegacyMode(self._legacyLifter)
        self.lifter.setGravity(self.getGravity(0))
        self.lifter.addInPattern('%fn-enter-%in')
        self.lifter.addAgainPattern('%fn-again-%in')
        self.lifter.addOutPattern('%fn-exit-%in')
        self.lifter.setOffset(floorOffset)
        self.lifter.setReach(reach)
        self.lifter.addCollider(self.cRayNodePath, self.avatarNodePath)

    def setupHeadSphere(self, avatarNodePath):
        collSphere = CollisionSphere(0, 0, 0, 1)
        collSphere.setTangible(1)
        collNode = CollisionNode('Flyer.cHeadCollSphere')
        collNode.setFromCollideMask(ToontownGlobals.CeilingBitmask)
        collNode.setIntoCollideMask(BitMask32.allOff())
        collNode.addSolid(collSphere)
        self.cHeadSphereNodePath = avatarNodePath.attachNewNode(collNode)
        self.cHeadSphereNodePath.setZ(base.localAvatar.getHeight() + 1.0)
        self.headCollisionEvent = CollisionHandlerEvent()
        self.headCollisionEvent.addInPattern('%fn-enter-%in')
        self.headCollisionEvent.addOutPattern('%fn-exit-%in')
        base.cTrav.addCollider(self.cHeadSphereNodePath,
                               self.headCollisionEvent)

    def setupFloorEventSphere(self, avatarNodePath, bitmask, avatarRadius):
        cSphere = CollisionSphere(0.0, 0.0, 0.0, 0.75)
        cSphereNode = CollisionNode('Flyer.cFloorEventSphere')
        cSphereNode.addSolid(cSphere)
        cSphereNodePath = avatarNodePath.attachNewNode(cSphereNode)
        cSphereNode.setFromCollideMask(bitmask)
        cSphereNode.setIntoCollideMask(BitMask32.allOff())
        self.floorCollisionEvent = CollisionHandlerEvent()
        self.floorCollisionEvent.addInPattern('%fn-enter-%in')
        self.floorCollisionEvent.addAgainPattern('%fn-again-%in')
        self.floorCollisionEvent.addOutPattern('%fn-exit-%in')
        base.cTrav.addCollider(cSphereNodePath, self.floorCollisionEvent)
        self.cFloorEventSphereNodePath = cSphereNodePath

    def deleteCollisions(self):
        GravityWalker.deleteCollisions(self)
        if self.cHeadSphereNodePath != None:
            base.cTrav.removeCollider(self.cHeadSphereNodePath)
            self.cHeadSphereNodePath.detachNode()
            self.cHeadSphereNodePath = None
            self.headCollisionsEvent = None
        if self.cFloorEventSphereNodePath != None:
            base.cTrav.removeCollider(self.cFloorEventSphereNodePath)
            self.cFloorEventSphereNodePath.detachNode()
            self.cFloorEventSphereNodePath = None
            self.floorCollisionEvent = None
        self.cRayNodePath.detachNode()
        del self.cRayNodePath
        self.cEventSphereNodePath.detachNode()
        del self.cEventSphereNodePath
        return

    def setCollisionsActive(self, active=1):
        if self.collisionsActive != active:
            if self.cHeadSphereNodePath != None:
                base.cTrav.removeCollider(self.cHeadSphereNodePath)
                if active:
                    base.cTrav.addCollider(self.cHeadSphereNodePath,
                                           self.headCollisionEvent)
            if self.cFloorEventSphereNodePath != None:
                base.cTrav.removeCollider(self.cFloorEventSphereNodePath)
                if active:
                    base.cTrav.addCollider(self.cFloorEventSphereNodePath,
                                           self.floorCollisionEvent)
        GravityWalker.setCollisionsActive(self, active)
        return

    def enableAvatarControls(self):
        pass

    def disableAvatarControls(self):
        pass

    def handleAvatarControls(self, task):
        pass
예제 #30
0
class GameContainer(ShowBase):
    def __init__(self):

        ShowBase.__init__(self)

        ########## Window configuration #########

        wp = WindowProperties()

        wp.setSize(1024, 860)
        wp.setTitle("")
        wp.setOrigin(-2, -2)

        self.win.requestProperties(wp)

        self.win.movePointer(0, wp.getXSize() / 2, wp.getYSize() / 2)
        print wp.getXSize() / 2, wp.getYSize() / 2

        ########## Gameplay settings #########

        self.gameMode = {"display": PLAY, "play": TERRAIN}

        self.level = 1.5

        self.mode_initialized = False

        ######### Camera #########

        self.disableMouse()

        self.mainCamera = Camera(self.camera)

        self.mainCamera.camObject.setHpr(0, 0, 0)

        self.loadLevel()

        ######### Events #########

        self.taskMgr.add(self.gameLoop, "gameLoop", priority=35)

        self.keys = {"w": 0, "s": 0, "a": 0, "d": 0, "space": 0, "escape": 0}

        self.accept("w", self.setKey, ["w", 1])
        self.accept("w-up", self.setKey, ["w", 0])
        self.accept("s", self.setKey, ["s", 1])
        self.accept("s-up", self.setKey, ["s", 0])
        self.accept("a", self.setKey, ["a", 1])
        self.accept("a-up", self.setKey, ["a", 0])
        self.accept("d", self.setKey, ["d", 1])
        self.accept("d-up", self.setKey, ["d", 0])
        self.accept("space", self.setKey, ["space", 1])
        self.accept("space-up", self.setKey, ["space", 0])
        self.accept("escape", self.setKey, ["escape", 1])
        self.accept("escape-up", self.setKey, ["escape", 0])
        self.accept("wheel_up", self.zoomCamera, [-1])
        self.accept("wheel_down", self.zoomCamera, [1])

        self.accept("window-event", self.handleWindowEvent)

        ######### GUI #########

        #self.fonts = {"failure" : loader.loadFont('myfont.ttf')}

        self.guiElements = []

        self._GCLK = None
        self._FT = None

        #Trigger game chain

        #self.enableParticles()

        #self.buildMainMenu()

    def setKey(self, key, value):

        self.keys[key] = value

    def zoomCamera(self, direction):

        if self.gameMode["play"] == TERRAIN:

            Camera.AVATAR_DIST += direction

    def toggleCursor(self, state):

        props = WindowProperties()
        props.setCursorHidden(state)
        base.win.requestProperties(props)

    def handleWindowEvent(self, window=None):

        wp = window.getProperties()

        self.win_center_x = wp.getXSize() / 2
        self.win_center_y = wp.getYSize() / 2

    def processKeys(self):

        if self.keys["escape"]:

            if self.gameMode["display"] == PLAY:

                self.switchDisplayMode(IN_GAME_MENU)

            elif self.gameMode["display"] == IN_GAME_MENU:

                self.switchDisplayMode(PLAY)

            self.setKey("escape", 0)

    ######### Level specific features #########

    def maintainTurrets(self):

        pass

    def switchDisplayMode(self, newGameMode):

        self.cleanupGUI()

        if self.gameMode["display"] == MAIN_MENU:

            pass

        elif self.gameMode["display"] == IN_GAME_MENU:

            if newGameMode == PLAY:

                render.clearFog()

                self.togglePhysicsPause()

            elif newGameMode == MAIN_MENU:

                pass

        elif self.gameMode["display"] == PLAY:

            if newGameMode == IN_GAME_MENU:

                self.togglePhysicsPause()

        self.gameMode["display"] = newGameMode

        self.mode_initialized = False

    def advanceLevel(self):

        self.level += .5

        self.loadLevel()

    def evenButtonPositions(self, button_spacing, button_height, num_buttons):

        centerOffset = (button_spacing / (2.0) if
                        (num_buttons % 2 == 0) else 0)

        buttonPositions = []

        current_pos = centerOffset + ((num_buttons - 1) / 2) * button_spacing

        for i in range(0, num_buttons):

            buttonPositions.append(current_pos + (button_height / 2.0))

            current_pos -= button_spacing

        return buttonPositions

    def buildInGameMenu(self):

        self.toggleCursor(False)

        resume_button = DirectButton(
            text="Resume",
            scale=.1,
            command=(lambda: self.switchDisplayMode(PLAY)),
            rolloverSound=None)
        main_menu_button = DirectButton(text="Main Menu",
                                        scale=.1,
                                        command=None,
                                        rolloverSound=None)
        options_button = DirectButton(text="Settings",
                                      scale=.1,
                                      command=None,
                                      rolloverSound=None)
        exit_button = DirectButton(text="Exit",
                                   scale=.1,
                                   command=exit,
                                   rolloverSound=None)

        BUTTON_SPACING = .2
        BUTTON_HEIGHT = resume_button.getSy()

        button_positions = self.evenButtonPositions(BUTTON_SPACING,
                                                    BUTTON_HEIGHT, 4)

        resume_button.setPos(Vec3(0, 0, button_positions[0]))
        main_menu_button.setPos(Vec3(0, 0, button_positions[1]))
        options_button.setPos(Vec3(0, 0, button_positions[2]))
        exit_button.setPos(Vec3(0, 0, button_positions[3]))

        self.guiElements.append(resume_button)
        self.guiElements.append(main_menu_button)
        self.guiElements.append(options_button)
        self.guiElements.append(exit_button)

    def buildMainMenu(self):

        self.toggleCursor(False)

        start_game_button = DirectButton(text="Start", scale=.1, command=None)
        select_level_button = DirectButton(text="Select Level",
                                           scale=.1,
                                           command=None)
        game_options_button = DirectButton(text="Settings",
                                           scale=.1,
                                           command=None)
        exit_button = DirectButton(text="Exit", scale=.1, command=exit)

        BUTTON_SPACING = .2
        BUTTON_HEIGHT = start_game_button.getSy()

        button_positions = self.evenButtonPositions(BUTTON_SPACING,
                                                    BUTTON_HEIGHT, 4)

        start_game_button.setPos(Vec3(0, 0, button_positions[0]))
        select_level_button.setPos(Vec3(0, 0, button_positions[1]))
        game_options_button.setPos(Vec3(0, 0, button_positions[2]))
        exit_button.setPos(Vec3(0, 0, button_positions[3]))

        self.guiElements.append(start_game_button)
        self.guiElements.append(select_level_button)
        self.guiElements.append(game_options_button)
        self.guiElements.append(exit_button)

        particles = Particles()
        particles.setPoolSize(1000)
        particles.setBirthRate(.1)
        particles.setLitterSize(10)
        particles.setLitterSpread(3)
        particles.setFactory("PointParticleFactory")
        particles.setRenderer("PointParticleRenderer")
        particles.setEmitter("SphereVolumeEmitter")
        particles.enable()

        self.effect = ParticleEffect("peffect", particles)
        self.effect.reparentTo(render)
        #self.effect.setPos(self.avatar.objectNP.getX(), self.avatar.objectNP.getY(), self.avatar.objectNP.getZ() + 5)
        self.effect.setPos(-1, 0, 0)
        self.effect.enable()

    def buildDeathScreen(self):

        self.toggleCursor(False)

        backFrame = DirectFrame(frameColor=(1, 0, 0, .7),
                                frameSize=(-.5, .5, -.3, .3),
                                pos=(0, 0, 0))

        deadMessage = DirectLabel(text="MISSION FAILURE",
                                  scale=.1,
                                  pos=(0, 0, .16),
                                  relief=None,
                                  text_font=None)

        restartButton = DirectButton(text="Restart",
                                     scale=.1,
                                     pos=(0, 0, -.1),
                                     command=self.resetLevel)

        deadMessage.reparentTo(backFrame)
        restartButton.reparentTo(backFrame)

        self.guiElements.append(backFrame)
        self.guiElements.append(deadMessage)
        self.guiElements.append(restartButton)

    def cleanupGUI(self):

        for guiElement in self.guiElements:

            guiElement.destroy()

    def loadSpaceTexture(self, level):

        if level < 10: return 'textures/space#.jpg'
        elif level < 15: pass

    def resetLevel(self):

        self.switchDisplayMode(PLAY)

        self.loadLevel(True)

    def loadLevel(self, reset=False):

        #Resets

        self.avatarActor = Actor("models/panda", {"walk": "models/panda-walk"})
        self.avatarActor.setScale(.5, .5, .5)
        self.avatarActor.setHpr(180, 0, 0)
        self.avatarActor.setCollideMask(BitMask32.allOff())

        self.asteroidManager = AsteroidManager()

        self.cTrav = CollisionTraverser()

        #Alternate modes

        if int(self.level) == self.level: self.gameMode["play"] = TERRAIN

        else: self.gameMode["play"] = SPACE

        #Specifics

        if self.gameMode["play"] == SPACE:

            if reset:

                self.avatar.reset()

            else:

                self.avatar = Avatar(self.avatarActor, self.level)

                self.avatar.objectNP.reparentTo(render)

            ########## Sky #########

            cubeMap = loader.loadCubeMap(self.loadSpaceTexture(self.level))
            self.spaceSkyBox = loader.loadModel('models/box')
            self.spaceSkyBox.setScale(100)
            self.spaceSkyBox.setBin('background', 0)
            self.spaceSkyBox.setDepthWrite(0)
            self.spaceSkyBox.setTwoSided(True)
            self.spaceSkyBox.setTexGen(TextureStage.getDefault(),
                                       TexGenAttrib.MWorldCubeMap)
            self.spaceSkyBox.setTexture(cubeMap, 1)
            parentNP = render.attachNewNode('parent')
            self.spaceSkyBox.reparentTo(parentNP)
            self.spaceSkyBox.setPos(-self.spaceSkyBox.getSx() / 2,
                                    -self.spaceSkyBox.getSy() / 2,
                                    -self.spaceSkyBox.getSz() / 2)

            ########## Collisions #########

            bound = self.avatarActor.getBounds()

            self.pandaBodySphere = CollisionSphere(
                bound.getCenter()[0] / self.avatar.objectNP.getSx() -
                self.avatar.objectNP.getX(),
                bound.getCenter()[1] / self.avatar.objectNP.getSx() -
                self.avatar.objectNP.getY(),
                bound.getCenter()[2] / self.avatar.objectNP.getSx() -
                self.avatar.objectNP.getZ(), 5)

            self.pandaBodySphere.setRadius(bound.getRadius() + 1)

            self.pandaBodySphereNode = CollisionNode("playerBodyRay")
            self.pandaBodySphereNode.addSolid(self.pandaBodySphere)
            self.pandaBodySphereNode.setFromCollideMask(BitMask32.bit(0))
            self.pandaBodySphereNode.setIntoCollideMask(BitMask32.allOff())

            self.pandaBodySphereNodepath = self.avatar.objectNP.attachNewNode(
                self.pandaBodySphereNode)
            self.pandaBodySphereNodepath.show()

            self.collisionNotifier = CollisionHandlerEvent()
            self.collisionNotifier.addInPattern("%fn-in")
            self.collisionNotifier.addOutPattern("%fn-out")

            self.cTrav.addCollider(self.pandaBodySphereNodepath,
                                   self.collisionNotifier)

            self.accept("playerGroundRayJumping-in",
                        self.avatar.handleCollisionEvent, ["in"])
            self.accept("playerGroundRayJumping-out",
                        self.avatar.handleCollisionEvent, ["out"])
            self.accept("playerBodyRay-in", self.avatar.handleCollisionEvent,
                        ["in"])

            self.asteroidManager.initialize(self.level)

        elif self.gameMode["play"] == TERRAIN:

            ########## Terrain #########

            #self.environ = loader.loadModel("../mystuff/test.egg")
            self.environ = loader.loadModel("models/environment")
            self.environ.setName("terrain")
            self.environ.reparentTo(render)
            self.environ.setPos(0, 0, 0)
            self.environ.setCollideMask(BitMask32.bit(0))

            ######### Physics #########

            self.enableParticles()

            gravityForce = LinearVectorForce(0, 0, -9.81)
            gravityForce.setMassDependent(False)
            gravityFN = ForceNode("world-forces")
            gravityFN.addForce(gravityForce)
            render.attachNewNode(gravityFN)
            base.physicsMgr.addLinearForce(gravityForce)

            self.avatarPhysicsActorNP = render.attachNewNode(
                ActorNode("player"))
            self.avatarPhysicsActorNP.node().getPhysicsObject().setMass(50.)
            self.avatarActor.reparentTo(self.avatarPhysicsActorNP)
            base.physicsMgr.attachPhysicalNode(
                self.avatarPhysicsActorNP.node())

            self.avatarPhysicsActorNP.setPos(15, 10, 5)

            ######### Game objects #########

            self.avatar = Avatar(self.avatarPhysicsActorNP, self.level)

            ######### Collisions #########

            self.pandaBodySphere = CollisionSphere(0, 0, 4, 3)

            self.pandaBodySphereNode = CollisionNode("playerBodySphere")
            self.pandaBodySphereNode.addSolid(self.pandaBodySphere)
            self.pandaBodySphereNode.setFromCollideMask(BitMask32.bit(0))
            self.pandaBodySphereNode.setIntoCollideMask(BitMask32.allOff())

            self.pandaBodySphereNodepath = self.avatar.objectNP.attachNewNode(
                self.pandaBodySphereNode)
            self.pandaBodySphereNodepath.show()

            self.pandaBodyCollisionHandler = PhysicsCollisionHandler()
            self.pandaBodyCollisionHandler.addCollider(
                self.pandaBodySphereNodepath, self.avatar.objectNP)

            #Keep player on ground

            self.pandaGroundSphere = CollisionSphere(0, 0, 1, 1)

            self.pandaGroundSphereNode = CollisionNode("playerGroundRay")
            self.pandaGroundSphereNode.addSolid(self.pandaGroundSphere)
            self.pandaGroundSphereNode.setFromCollideMask(BitMask32.bit(0))
            self.pandaGroundSphereNode.setIntoCollideMask(BitMask32.allOff())

            self.pandaGroundSphereNodepath = self.avatar.objectNP.attachNewNode(
                self.pandaGroundSphereNode)
            self.pandaGroundSphereNodepath.show()

            self.pandaGroundCollisionHandler = PhysicsCollisionHandler()
            self.pandaGroundCollisionHandler.addCollider(
                self.pandaGroundSphereNodepath, self.avatar.objectNP)

            #Notify when player lands

            self.pandaGroundRayJumping = CollisionSphere(0, 0, 1, 1)

            self.pandaGroundRayNodeJumping = CollisionNode(
                "playerGroundRayJumping")
            self.pandaGroundRayNodeJumping.addSolid(self.pandaGroundRayJumping)
            self.pandaGroundRayNodeJumping.setFromCollideMask(BitMask32.bit(0))
            self.pandaGroundRayNodeJumping.setIntoCollideMask(
                BitMask32.allOff())

            self.pandaGroundRayNodepathJumping = self.avatar.objectNP.attachNewNode(
                self.pandaGroundRayNodeJumping)
            self.pandaGroundRayNodepathJumping.show()

            self.collisionNotifier = CollisionHandlerEvent()
            self.collisionNotifier.addInPattern("%fn-in")
            self.collisionNotifier.addOutPattern("%fn-out")

            self.cTrav.addCollider(self.pandaGroundSphereNodepath,
                                   self.pandaGroundCollisionHandler)
            self.cTrav.addCollider(self.pandaGroundRayNodepathJumping,
                                   self.collisionNotifier)
            self.cTrav.addCollider(self.pandaBodySphereNodepath,
                                   self.pandaBodyCollisionHandler)

            self.accept("playerGroundRayJumping-in",
                        self.avatar.handleCollisionEvent, ["in"])
            self.accept("playerGroundRayJumping-out",
                        self.avatar.handleCollisionEvent, ["out"])
            self.accept("playerBodyRay-in", self.avatar.handleCollisionEvent,
                        ["in"])

    def togglePhysicsPause(self):

        if (self._GCLK == None):

            self.disableParticles()

            self._GCLK = ClockObject.getGlobalClock()
            self._FT = self._GCLK.getFrameTime()
            self._GCLK.setMode(ClockObject.MSlave)

        else:

            self._GCLK.setRealTime(self._FT)
            self._GCLK.setMode(ClockObject.MNormal)

            self.enableParticles()

            self._GCLK = None

    def gameLoop(self, task):

        dt = globalClock.getDt()

        self.processKeys()

        if self.gameMode["display"] == MAIN_MENU:

            if not self.mode_initialized:

                self.buildMainMenu()

                self.mode_initialized = True

        if self.gameMode["display"] == IN_GAME_MENU:

            if not self.mode_initialized:

                #Fog out background

                inGameMenuFogColor = (50, 150, 50)

                inGameMenuFog = Fog("inGameMenuFog")

                inGameMenuFog.setMode(Fog.MExponential)
                inGameMenuFog.setColor(*inGameMenuFogColor)
                inGameMenuFog.setExpDensity(.01)

                render.setFog(inGameMenuFog)

                self.buildInGameMenu()

                self.mode_initialized = True

        if self.gameMode["display"] == DEAD:

            if not self.mode_initialized:

                self.buildDeathScreen()

                self.mode_initialized = True

        if self.gameMode["display"] == PLAY:

            alive = self.avatar.states["alive"]

            if not self.mode_initialized:

                self.toggleCursor(True)

                self.last_mouse_x = self.win.getPointer(0).getX()
                self.last_mouse_y = self.win.getPointer(0).getY()

                self.mode_initialized = True

            if self.gameMode["play"] == TERRAIN:

                if alive:

                    self.maintainTurrets()
                    self.avatar.move(dt)

                else:
                    self.switchDisplayMode(DEAD)

            elif self.gameMode["play"] == SPACE:

                if alive:

                    self.asteroidManager.maintainAsteroidField(
                        self.avatar.objectNP.getPos(), self.avatar.speed,
                        Camera.AVATAR_DIST, dt)

                else:
                    self.switchDisplayMode(DEAD)

            if alive:

                #Handle keyboard input

                self.avatar.handleKeys(self.keys, self.gameMode["play"])

                ########## Mouse-based viewpoint rotation ##########

                mouse_pos = self.win.getPointer(0)

                current_mouse_x = mouse_pos.getX()
                current_mouse_y = mouse_pos.getY()

                #Side to side

                if self.gameMode["play"] == TERRAIN:

                    mouse_shift_x = current_mouse_x - self.last_mouse_x
                    self.last_mouse_x = current_mouse_x

                    if current_mouse_x < 5 or current_mouse_x >= (
                            self.win_center_x * 1.5):

                        base.win.movePointer(0, self.win_center_x,
                                             current_mouse_y)
                        self.last_mouse_x = self.win_center_x

                    yaw_shift = -((mouse_shift_x) * Camera.ROT_RATE[0])

                    self.avatar.yawRot += yaw_shift

                    self.avatar.objectNP.setH(self.avatar.yawRot)

                #Up and down

                mouse_shift_y = current_mouse_y - self.last_mouse_y
                self.last_mouse_y = current_mouse_y

                if current_mouse_y < 5 or current_mouse_y >= (
                        self.win_center_y * 1.5):

                    base.win.movePointer(0, current_mouse_x, self.win_center_y)
                    self.last_mouse_y = self.win_center_y

                pitch_shift = -((mouse_shift_y) * Camera.ROT_RATE[1])

                self.mainCamera.pitchRot += pitch_shift

                if self.mainCamera.pitchRot > Camera.FLEX_ROT_BOUND[0]:

                    self.mainCamera.pitchRot = Camera.FLEX_ROT_BOUND[0]

                elif self.mainCamera.pitchRot < -Camera.FLEX_ROT_BOUND[0]:

                    self.mainCamera.pitchRot = -Camera.FLEX_ROT_BOUND[0]

                xy_plane_cam_dist = Camera.AVATAR_DIST

                cam_x_adjust = xy_plane_cam_dist * sin(
                    radians(self.avatar.yawRot))
                cam_y_adjust = xy_plane_cam_dist * cos(
                    radians(self.avatar.yawRot))
                cam_z_adjust = Camera.ELEVATION

                self.mainCamera.camObject.setH(self.avatar.yawRot)
                self.mainCamera.camObject.setP(self.mainCamera.pitchRot)

                self.mainCamera.camObject.setPos(
                    self.avatar.objectNP.getX() + cam_x_adjust,
                    self.avatar.objectNP.getY() - cam_y_adjust,
                    self.avatar.objectNP.getZ() + cam_z_adjust)

                #Find collisions

                self.cTrav.traverse(render)

        return Task.cont