| 123456789101112131415161718192021222324252627282930313233343536373839404142434445464748495051525354555657585960616263646566676869707172737475767778798081828384858687888990919293949596979899100101102103104105106107108109110111112113114115116117118119120121122123124125126127128129130131132133134135136137138139140141142143144145146147148149150151152153154155156157158159160161162163164165166167168169170171172173174175176177178179180181182183184 |
- from direct.showbase.ShowBase import ShowBase
- from panda3d.core import Plane, Vec3, Point3, CardMaker, MouseButton
- from direct.task import Task
- from direct.actor.Actor import Actor
- from direct.interval.IntervalGlobal import Sequence
- from panda3d import navigation
- from panda3d import navmeshgen
- from panda3d.core import PointLight,DirectionalLight
- from panda3d.core import LPoint3
- from panda3d.core import PTA_LVecBase3
- from panda3d.core import LVecBase3
- from panda3d.core import LineSegs
- from panda3d.core import NodePath
- import math
- import time
- class MyApp(ShowBase):
- def __init__(self):
- ShowBase.__init__(self)
- # Setting up light for better view.
- plight = PointLight('plight')
- plight.setColor((0.9, 0.9, 0.9, 0.5))
- plnp = render.attachNewNode(plight)
- plnp.setPos(10, 20, 0)
- render.setLight(plnp)
- dlight = DirectionalLight('dlight')
- dlight.setColor((0.8, 0.5, 0.5, 1))
- dlnp = render.attachNewNode(dlight)
- dlnp.setHpr(0, -60, 0)
- render.setLight(dlnp)
- # Loading the model
- self.scene = self.loader.loadModel("village.obj")
- self.scene.reparentTo(self.render)
- self.scene.setP(90)
-
- self.scene.setScale(0.25, 0.25, 0.25)
- self.scene.flatten_light()
- self.scene.setPos(-8, 42, 0)
-
- # mouseclick
- self.camera.setPos(0, 60, 500)
- self.camera.lookAt(0, 0, 0)
- z = 0
- self.plane = Plane(Vec3(0, 0, 1), Point3(0, 0, z))
- cm = CardMaker("blah")
- cm.setFrame(-100, 100, -100, 100)
- taskMgr.add(self.__getMousePos, "_YourClass__getMousePos")
- # mouseclick end
- # NavMeshBuilder is a class that is responsible for building the polygon meshes and navigation meshes.
- self.builder = navmeshgen.NavMeshBuilder()
- self.structBuilder = navmeshgen.BuildSettings()
- self.structBuilder.cell_size = 1;
- # Take Nodepath as input. Nodepath should contain the required geometry.
- self.builder.fromNodePath(self.scene)
- #self.builder.setActorRadius(5)
- self.builder.set_actor_height(10)
- self.navmesh = self.builder.build()
-
- self.navmeshnode = navigation.NavMeshNode("firstnavmeshnode",self.navmesh)
- self.navmeshnodepath = self.scene.attachNewNode(self.navmeshnode)
- self.accept("s",self.navmeshnodepath.show)
- self.accept("h",self.navmeshnodepath.hide)
- # uncomment below line to write to bam
- #self.navmeshnodepath.write_bam_file("firstnavmeshnode.bam")
- # uncomment below line to read from bam
- #self.navmesh = loader.loadModel("firstnavmeshnode.bam")
-
- self.tempActor = Actor("models/panda", {"walk" : "models/panda-walk"})
- self.tempActor.reparentTo(self.scene)
- self.pos1 = self.tempActor.getPos()
- self.pos2 = self.pos1
- self.query = navigation.NavMeshQuery(self.navmesh)
-
- # #self.query.setNavQuery(self.navmesh)
- self.query.nearestPoint(self.pos1)
- # print(pos1)
- self.tempActor.setPos(self.pos1)
- self.tempActor2 = Actor("models/panda", {"walk" : "models/panda-walk"})
- self.tempActor2.reparentTo(self.scene)
- # Load and transform the panda actor.
- self.pandaActor = Actor("models/panda-model",
- {"walk": "models/panda-walk4"})
- self.pandaActor.setScale(0.01, 0.01, 0.01)
- self.pandaActor.reparentTo(self.scene)
- self.pandaActor.loop("walk")
-
- self.pandaSequence = Sequence()
- self.pandaSequence.start()
- self.lineNodePath = NodePath()
- self.lineNodePath2 = NodePath()
- def __getMousePos(self,task):
- if base.mouseWatcherNode.hasMouse() and base.mouseWatcherNode.isButtonDown(MouseButton.one()):
- mpos = base.mouseWatcherNode.getMouse()
- pos3d = Point3()
- nearPoint = Point3()
- farPoint = Point3()
- base.camLens.extrude(mpos, nearPoint, farPoint)
-
- if self.plane.intersectsLine(pos3d,
- self.scene.getRelativePoint(camera, nearPoint),
- self.scene.getRelativePoint(camera, farPoint)):
-
- if abs(self.pos2[0]-pos3d[0]) < 1:
- return task.again
-
- self.pos2 = pos3d
-
- self.pos1 = self.pandaActor.get_pos()
- self.pandaSequence.finish()
-
- self.query.nearestPoint(self.pos2)
- # print(pos2)
- self.tempActor2.setPos(self.pos2)
- path = self.query.findPath(self.pos1, self.pos2);
- print("path.size(): ", len(path));
- self.pathLine = LineSegs()
- self.pathLine.setColor(0,1,0)
- self.pathLine.setThickness(5)
- self.pathLine2 = LineSegs()
- self.pathLine2.setColor(1,1,0)
- self.pathLine2.setThickness(5)
- for i in range(len(path)):
- self.pathLine.drawTo(path[i])
- self.pathLine.drawTo(self.pos2)
- self.lineNode = self.pathLine.create()
- self.lineNodePath.remove_node()
- self.lineNodePath = self.scene.attachNewNode(self.lineNode)
- self.lineNodePath.setZ(1)
- path = self.query.findStraightPath(self.pos1, self.pos2, 0);
- print("path.size(): ", len(path));
- for i in range(len(path)):
- self.pathLine2.drawTo(path[i])
-
- self.lineNode2 = self.pathLine2.create()
- self.lineNodePath2.remove_node()
- self.lineNodePath2 = self.scene.attachNewNode(self.lineNode2)
- self.lineNodePath2.setZ(2)
-
- self.pandaSequence = Sequence()
- current_dir = self.pandaActor.get_hpr()
- for i in range(len(path)-1):
- print(i, path[i], path[i+1])
- vec = [ path[i+1][0] - path[i][0] , path[i+1][1] - path[i][1] ]
- cosval = -1 * vec[1] / math.sqrt( vec[0]**2 + vec[1]**2 )
- theta = math.acos(cosval) * 180/math.pi
- if vec[0] < 0:
- theta = 360 - theta
- new_dir = LPoint3(theta, current_dir[1], current_dir[2])
- rotate_speed = 90
- #rotate_time = abs(theta-current_dir[0])/rotate_speed
- rotate_time = 0
- self.pandaSequence.append(self.pandaActor.hprInterval(rotate_time, new_dir, current_dir))
- speed = 6
- dist = math.dist(path[i+1],path[i])
- print(dist)
- self.pandaSequence.append(self.pandaActor.posInterval(dist/speed, path[i+1], path[i]))
- current_dir = new_dir
- self.pandaSequence.start()
- self.pos1 = self.pos2
- return task.again
- app = MyApp()
- app.run()
|