mirror of
https://github.com/panda3d/panda3d.git
synced 2025-10-02 09:52:27 -04:00
added optional 'from' collider node parameter to optimize triggered phase changes
This commit is contained in:
parent
34793b5be7
commit
8e9d2b85ab
@ -18,7 +18,8 @@ class DistancePhasedNode(PhasedObject, DirectObject, NodePath):
|
|||||||
exitting the largest distance sphere
|
exitting the largest distance sphere
|
||||||
- What the load/unload functions are
|
- What the load/unload functions are
|
||||||
- What sort of events to listen for when a collision occurs
|
- What sort of events to listen for when a collision occurs
|
||||||
- (Optional) - a collision bitmask for the phase collision spheres
|
- (Optional) A collision bitmask for the phase collision spheres
|
||||||
|
- (Optional) A 'from' collision node to collide into our 'into' spheres
|
||||||
|
|
||||||
You specify the distances and function names by the phaseParamMap
|
You specify the distances and function names by the phaseParamMap
|
||||||
parameter to __init__(). For example:
|
parameter to __init__(). For example:
|
||||||
@ -30,6 +31,15 @@ class DistancePhasedNode(PhasedObject, DirectObject, NodePath):
|
|||||||
def unloadPhaseAlias(self):
|
def unloadPhaseAlias(self):
|
||||||
pass
|
pass
|
||||||
|
|
||||||
|
If the 'fromCollideNode' is supplied, we will set up our own
|
||||||
|
traverser and only traverse below this node. It will send out
|
||||||
|
events of the form '<enterPrefix>%in' and '<exitPrefix>%in' in
|
||||||
|
order to match the main collision traverser's patterns. Note
|
||||||
|
that this will only be used after a reset or phase change in
|
||||||
|
order to fully transition to the correct phase in a single pass.
|
||||||
|
Most of the time, it will be reacting to events from the main
|
||||||
|
collision traverser.
|
||||||
|
|
||||||
IMPORTANT!: The following only applies when autoCleanup == True:
|
IMPORTANT!: The following only applies when autoCleanup == True:
|
||||||
If you unload the last phase, by either calling
|
If you unload the last phase, by either calling
|
||||||
cleanup() or by exitting the last phase's distance,
|
cleanup() or by exitting the last phase's distance,
|
||||||
@ -70,7 +80,8 @@ class DistancePhasedNode(PhasedObject, DirectObject, NodePath):
|
|||||||
def __init__(self, name, phaseParamMap = {},
|
def __init__(self, name, phaseParamMap = {},
|
||||||
autoCleanup = True,
|
autoCleanup = True,
|
||||||
enterPrefix = 'enter', exitPrefix = 'exit',
|
enterPrefix = 'enter', exitPrefix = 'exit',
|
||||||
phaseCollideMask = BitMask32.allOn()):
|
phaseCollideMask = BitMask32.allOn(),
|
||||||
|
fromCollideNode = None):
|
||||||
NodePath.__init__(self, name)
|
NodePath.__init__(self, name)
|
||||||
self.phaseParamMap = phaseParamMap
|
self.phaseParamMap = phaseParamMap
|
||||||
self.phaseParamList = sorted(phaseParamMap.items(),
|
self.phaseParamList = sorted(phaseParamMap.items(),
|
||||||
@ -81,9 +92,11 @@ class DistancePhasedNode(PhasedObject, DirectObject, NodePath):
|
|||||||
self.__id = self.__allocateId()
|
self.__id = self.__allocateId()
|
||||||
|
|
||||||
self.autoCleanup = autoCleanup
|
self.autoCleanup = autoCleanup
|
||||||
self.phaseCollideMask = phaseCollideMask
|
|
||||||
self.enterPrefix = enterPrefix
|
self.enterPrefix = enterPrefix
|
||||||
self.exitPrefix = exitPrefix
|
self.exitPrefix = exitPrefix
|
||||||
|
self.phaseCollideMask = phaseCollideMask
|
||||||
|
self.cTrav = base.cTrav
|
||||||
|
self.fromCollideNode = fromCollideNode
|
||||||
self._colSpheres = []
|
self._colSpheres = []
|
||||||
|
|
||||||
self.reset()
|
self.reset()
|
||||||
@ -94,8 +107,8 @@ class DistancePhasedNode(PhasedObject, DirectObject, NodePath):
|
|||||||
def __repr__(self):
|
def __repr__(self):
|
||||||
outStr = 'DistancePhasedObject('
|
outStr = 'DistancePhasedObject('
|
||||||
outStr += '%s' % `self.getName()`
|
outStr += '%s' % `self.getName()`
|
||||||
for param, value in zip(('phaseParamMap', 'autoCleanup', 'enterPrefix', 'exitPrefix', 'phaseCollideMask'),
|
for param, value in zip(('phaseParamMap', 'autoCleanup', 'enterPrefix', 'exitPrefix', 'phaseCollideMask', 'fromCollideNode'),
|
||||||
('{}', 'True','\'enter\'','\'exit\'','BitMask32.allOn()')):
|
('{}', 'True','\'enter\'','\'exit\'','BitMask32.allOn()','None')):
|
||||||
outStr += eval('(\', ' + param + ' = %s\' % `self.' + param + '`,\'\')[self.' + param + ' == ' + value + ']')
|
outStr += eval('(\', ' + param + ' = %s\' % `self.' + param + '`,\'\')[self.' + param + ' == ' + value + ']')
|
||||||
outStr += ')'
|
outStr += ')'
|
||||||
return outStr
|
return outStr
|
||||||
@ -143,6 +156,12 @@ class DistancePhasedNode(PhasedObject, DirectObject, NodePath):
|
|||||||
cSphereNodePath.stash()
|
cSphereNodePath.stash()
|
||||||
# cSphereNodePath.show() # For debugging
|
# cSphereNodePath.show() # For debugging
|
||||||
self._colSpheres.append(cSphereNodePath)
|
self._colSpheres.append(cSphereNodePath)
|
||||||
|
if self.fromCollideNode:
|
||||||
|
self.cTrav = CollisionTraverser()
|
||||||
|
cHandler = CollisionHandlerEvent()
|
||||||
|
cHandler.addInPattern(self.enterPrefix + '%in')
|
||||||
|
cHandler.addOutPattern(self.exitPrefix + '%in')
|
||||||
|
self.cTrav.addCollider(self.fromCollideNode,cHandler)
|
||||||
|
|
||||||
self.__enableCollisions(-1)
|
self.__enableCollisions(-1)
|
||||||
|
|
||||||
@ -218,11 +237,16 @@ class DistancePhasedNode(PhasedObject, DirectObject, NodePath):
|
|||||||
phasing process in one frame in the cases where
|
phasing process in one frame in the cases where
|
||||||
we cross more than one phase border.
|
we cross more than one phase border.
|
||||||
"""
|
"""
|
||||||
# we use 'render'here since if we only try to
|
if self.cTrav:
|
||||||
# traverse ourself, we end up calling exit
|
if self.cTrav is base.cTrav:
|
||||||
# events for the rest of the eventHandlers. >:(
|
# we use 'render'here since if we only try to
|
||||||
if base.cTrav:
|
# traverse ourself, we end up calling exit
|
||||||
base.cTrav.traverse(render)
|
# events for the rest of the eventHandlers.
|
||||||
|
# Consider supplying the fromCollideNode parameter.
|
||||||
|
self.cTrav.traverse(render)
|
||||||
|
else:
|
||||||
|
# Only traverse ourself
|
||||||
|
self.cTrav.traverse(self)
|
||||||
base.eventMgr.doEvents()
|
base.eventMgr.doEvents()
|
||||||
|
|
||||||
class BufferedDistancePhasedNode(DistancePhasedNode):
|
class BufferedDistancePhasedNode(DistancePhasedNode):
|
||||||
@ -243,7 +267,7 @@ class BufferedDistancePhasedNode(DistancePhasedNode):
|
|||||||
notify = directNotify.newCategory("BufferedDistancePhasedObject")
|
notify = directNotify.newCategory("BufferedDistancePhasedObject")
|
||||||
|
|
||||||
def __init__(self, name, bufferParamMap = {}, autoCleanup = True,
|
def __init__(self, name, bufferParamMap = {}, autoCleanup = True,
|
||||||
enterPrefix = 'enter', exitPrefix = 'exit', phaseCollideMask = BitMask32.allOn()):
|
enterPrefix = 'enter', exitPrefix = 'exit', phaseCollideMask = BitMask32.allOn(), fromCollideNode = None):
|
||||||
sParams = dict(bufferParamMap)
|
sParams = dict(bufferParamMap)
|
||||||
for key in sParams:
|
for key in sParams:
|
||||||
sParams[key] = sParams[key][0]
|
sParams[key] = sParams[key][0]
|
||||||
@ -252,7 +276,8 @@ class BufferedDistancePhasedNode(DistancePhasedNode):
|
|||||||
autoCleanup = autoCleanup,
|
autoCleanup = autoCleanup,
|
||||||
enterPrefix = enterPrefix,
|
enterPrefix = enterPrefix,
|
||||||
exitPrefix = exitPrefix,
|
exitPrefix = exitPrefix,
|
||||||
phaseCollideMask = phaseCollideMask)
|
phaseCollideMask = phaseCollideMask,
|
||||||
|
fromCollideNode = fromCollideNode)
|
||||||
self.bufferParamMap = bufferParamMap
|
self.bufferParamMap = bufferParamMap
|
||||||
self.bufferParamList = sorted(bufferParamMap.items(),
|
self.bufferParamList = sorted(bufferParamMap.items(),
|
||||||
key = lambda x: x[1],
|
key = lambda x: x[1],
|
||||||
@ -261,8 +286,8 @@ class BufferedDistancePhasedNode(DistancePhasedNode):
|
|||||||
def __repr__(self):
|
def __repr__(self):
|
||||||
outStr = 'BufferedDistancePhasedNode('
|
outStr = 'BufferedDistancePhasedNode('
|
||||||
outStr += '%s' % `self.getName()`
|
outStr += '%s' % `self.getName()`
|
||||||
for param, value in zip(('bufferParamMap', 'autoCleanup', 'enterPrefix', 'exitPrefix', 'phaseCollideMask'),
|
for param, value in zip(('bufferParamMap', 'autoCleanup', 'enterPrefix', 'exitPrefix', 'phaseCollideMask', 'fromCollideNode'),
|
||||||
('{}', 'True','\'enter\'','\'exit\'','BitMask32.allOn()')):
|
('{}', 'True','\'enter\'','\'exit\'','BitMask32.allOn()', 'None')):
|
||||||
outStr += eval('(\', ' + param + ' = %s\' % `self.' + param + '`,\'\')[self.' + param + ' == ' + value + ']')
|
outStr += eval('(\', ' + param + ' = %s\' % `self.' + param + '`,\'\')[self.' + param + ' == ' + value + ']')
|
||||||
outStr += ')'
|
outStr += ')'
|
||||||
return outStr
|
return outStr
|
||||||
@ -294,8 +319,8 @@ if __debug__ and 0:
|
|||||||
cNode.addSolid(cSphere)
|
cNode.addSolid(cSphere)
|
||||||
cNodePath = NodePath(cNode)
|
cNodePath = NodePath(cNode)
|
||||||
cNodePath.reparentTo(base.cam)
|
cNodePath.reparentTo(base.cam)
|
||||||
#cNodePath.show()
|
# cNodePath.show()
|
||||||
#cNodePath.setPos(25,0,0)
|
# cNodePath.setPos(25,0,0)
|
||||||
|
|
||||||
base.cTrav = CollisionTraverser()
|
base.cTrav = CollisionTraverser()
|
||||||
|
|
||||||
@ -307,7 +332,9 @@ if __debug__ and 0:
|
|||||||
base.cTrav.addCollider(cNodePath,eventHandler)
|
base.cTrav.addCollider(cNodePath,eventHandler)
|
||||||
|
|
||||||
p = BufferedDistancePhasedNode('p',{'At':(10,20),'Near':(100,200),'Far':(1000, 1020)},
|
p = BufferedDistancePhasedNode('p',{'At':(10,20),'Near':(100,200),'Far':(1000, 1020)},
|
||||||
autoCleanup = True)
|
autoCleanup = False,
|
||||||
|
fromCollideNode = cNodePath,
|
||||||
|
)
|
||||||
|
|
||||||
p.reparentTo(render)
|
p.reparentTo(render)
|
||||||
p._DistancePhasedNode__oneTimeCollide()
|
p._DistancePhasedNode__oneTimeCollide()
|
||||||
|
Loading…
x
Reference in New Issue
Block a user