*** empty log message ***

This commit is contained in:
Joe Shochet 2001-01-24 00:13:11 +00:00
parent 55016c526a
commit 87d951c0c5
5 changed files with 102 additions and 59 deletions

View File

@ -4,9 +4,11 @@ import TypedObject
WrapperClassMap = {}
DowncastMap = {}
# For testing, you can turn verbose and debug on
# FFIConstants.notify.setVerbose(1)
# FFIConstants.notify.setDebug(1)
FFIConstants.notify.setVerbose(1)
FFIConstants.notify.setDebug(1)
# Register a python class in the type map if it is a typed object
@ -30,39 +32,66 @@ class FFIExternalObject:
# Base destructor in case you do not define one
pass
def getDowncastFunctions(self, thisClass, baseClass, chain):
if (thisClass == baseClass):
# Found it, return true
return 1
def getLineage(self, thisClass, targetBaseClass):
# Recursively determine the path in the heirarchy tree from thisClass
# to the targetBaseClass
return self.getLineageInternal(thisClass, targetBaseClass, [thisClass])
def getLineageInternal(self, thisClass, targetBaseClass, chain):
# Recursively determine the path in the heirarchy tree from thisClass
# to the targetBaseClass
FFIConstants.notify.debug('getLineageInternal: checking %s to %s'
% (thisClass.__name__, targetBaseClass.__name__))
if (targetBaseClass in thisClass.__bases__):
# Found a link
return chain + [targetBaseClass]
elif (len(thisClass.__bases__) == 0):
# Not here, return 0
# No possible links
return 0
else:
# Look recursively in the classes thisClass inherits from
# recurse
for base in thisClass.__bases__:
# If it finds it, append the base class's downcast function
# to the chain if it has one
if self.getDowncastFunctions(base, baseClass, chain):
downcastFuncName = ('downcastTo' + thisClass.__name__
+ 'From' + base.__name__)
# Look over this classes global modules dictionaries
# for the downcast function name
for globmod in self.__class__.__CModuleDowncasts__:
if globmod.__dict__.has_key(downcastFuncName):
func = globmod.__dict__[downcastFuncName]
FFIConstants.notify.debug('Found downcast function %s in %s'
% (downcastFuncName, globmod.__name__))
chain.append(func)
return chain
else:
FFIConstants.notify.debug('Did not find downcast function %s in %s'
% (downcastFuncName, globmod.__name__))
# In any case, return the chain
return chain
# Probably went up the wrong tree and did not find the rootClass
else:
return []
res = self.getLineageInternal(base, targetBaseClass, chain+[base])
if res:
# Actually, we want them in the reverse order
res.reverse()
FFIConstants.notify.debug('getLineageInternal: found path: ' + `res`)
return res
# Not found anywhere
return 0
def getDowncastFunctions(self, thisClass, baseClass):
FFIConstants.notify.debug(
'getDowncastFunctions: Looking for downcast function from %s to %s'
% (baseClass.__name__, thisClass.__name__))
lineage = self.getLineage(thisClass, baseClass)
# Start with an empty list of downcast functions
downcastFunctionList = []
# If it could not find the baseClass anywhere in the lineage, return empty
if not lineage:
return []
# Walk along the lineage looking for downcast functions from class to class+1
for i in range((len(lineage) - 1)):
fromClass = lineage[i]
toClass = lineage[i+1]
downcastFuncName = ('downcastTo' + toClass.__name__
+ 'From' + fromClass.__name__)
# Look over this classes global modules dictionaries
# for the downcast function name
for globmod in fromClass.__CModuleDowncasts__:
if globmod.__dict__.has_key(downcastFuncName):
func = globmod.__dict__[downcastFuncName]
FFIConstants.notify.debug(
'getDowncastFunctions: Found downcast function %s in %s'
% (downcastFuncName, globmod.__name__))
downcastFunctionList.append(func)
else:
FFIConstants.notify.debug(
'getDowncastFunctions: Did not find downcast function %s in %s'
% (downcastFuncName, globmod.__name__))
return downcastFunctionList
def setPointer(self):
if (self.this == 0):
@ -96,24 +125,27 @@ class FFIExternalObject:
else:
return None
def downcast(self, specificClass):
FFIConstants.notify.debug('downcasting from %s to %s' % \
(self.__class__.__name__, specificClass.__name__))
downcastChain = self.getDowncastFunctions(specificClass, self.__class__, [])
FFIConstants.notify.debug('downcast chain: ' + `downcastChain`)
newObject = self
if (downcastChain == None):
return newObject
elif (downcastChain == 1):
return newObject
elif (downcastChain == 0):
return newObject
def downcast(self, toClass):
fromClass = self.__class__
FFIConstants.notify.debug('downcast: downcasting from %s to %s' % \
(fromClass.__name__, toClass.__name__))
# Check the cache to see if we have looked this up before
if DowncastMap.has_key((fromClass, toClass)):
downcastChain = DowncastMap[(fromClass, toClass)]
FFIConstants.notify.debug('downcast: found cached downcast chain: ' + `downcastChain`)
else:
for downcastFunc in downcastChain:
FFIConstants.notify.debug('downcasting %s using %s' % \
(newObject.__class__.__name__, downcastFunc))
newObject = downcastFunc(newObject)
return newObject
downcastChain = self.getDowncastFunctions(toClass, fromClass)
FFIConstants.notify.debug('downcast: computed downcast chain: ' + `downcastChain`)
# Store it for next time
DowncastMap[(fromClass, toClass)] = downcastChain
newObject = self
for downcastFunc in downcastChain:
FFIConstants.notify.debug('downcast: downcasting %s using %s' % \
(newObject.__class__.__name__, downcastFunc))
newObject = downcastFunc(newObject)
return newObject
def compareTo(self, other):
# By default, we compare the C++ pointers

View File

@ -721,7 +721,7 @@ class FFIInterrogateDatabase:
# Output all the imports based on this list of functions
outputGlobalFileImports(downcastFile, self.environment.downcastFunctions, CModuleName)
for type in self.environment.downcastFunctions:
type.generateGlobalCode(downcastFile)
type.generateGlobalDowncastCode(downcastFile)
FFIConstants.notify.info( 'Generating global value code...')
globalFile = constructGlobalFile(codeDir, CModuleName)

View File

@ -31,18 +31,18 @@ methodRenameDictionary = {
'operator-' : '__sub__',
'operator*' : '__mul__',
'operator/' : '__div__',
'operator+=' : 'addEqual',
'operator-=' : 'subtractEqual',
'operator*=' : 'multiplyEqual',
'operator/=' : 'divEqual',
'operator+=' : '__iadd__',
'operator-=' : '__isub__',
'operator*=' : '__imul__',
'operator/=' : '__idiv__',
'operator,' : 'concatenate',
'operator|=' : 'bitwiseOrEqual',
'operator&=' : 'bitwiseAndEqual',
'operator^=' : 'bitwiseXorEqual',
'operator|=' : '__ior__',
'operator&=' : '__iand__',
'operator^=' : '__ixor__',
'operator~=' : 'bitwiseNotEqual',
'operator->' : 'dereference',
'operator<<=' : 'leftShiftEqual',
'operator>>=' : 'rightShiftEqual',
'operator<<=' : '__ilshift__',
'operator>>=' : '__irshift__',
'print' : 'Cprint'
}

View File

@ -132,6 +132,13 @@ class GlobalFunctionSpecification(FunctionSpecification):
self.outputHeader(file)
self.outputBody(file)
self.outputFooter(file)
# Use generateCode when creating a global (non-class) function
def generateGlobalDowncastCode(self, file):
self.outputHeader(file)
self.outputBody(file, 0) # no downcast
self.outputFooter(file)
# Use generateMethodCode when creating a global->class function
def generateMethodCode(self, methodClass, file, nesting):
self.outputMethodHeader(methodClass, file, nesting)
@ -149,7 +156,8 @@ class GlobalFunctionSpecification(FunctionSpecification):
if (i < (len(argTypes)-1)):
file.write(', ')
file.write('):\n')
def outputBody(self, file):
def outputBody(self, file, needsDowncast=1):
# The method body will look something like
# returnValue = PandaGlobal.method(arg)
# returnObject = NodePath()
@ -167,7 +175,7 @@ class GlobalFunctionSpecification(FunctionSpecification):
file.write(', ')
file.write(')\n')
returnType = self.typeDescriptor.returnType.recursiveTypeDescriptor()
returnType.generateReturnValueWrapper(file, self.typeDescriptor.userManagesMemory, 1, 1)
returnType.generateReturnValueWrapper(file, self.typeDescriptor.userManagesMemory, needsDowncast, 1)
def outputFooter(self, file):
indent(file, 0, '\n')

View File

@ -158,6 +158,7 @@ class ShowBase:
self.trackball.reparentTo(self.dataUnused)
self.mouse2cam.reparentTo(self.dataUnused)
self.mouseInterface = None
self.mouseInterfaceNode = None
def setMouseOnArc(self, newArc):
self.mouse2cam.node().setArc(newArc)
@ -170,6 +171,7 @@ class ShowBase:
self.trackball.reparentTo(self.dataUnused)
# Update the mouseInterface to point to the drive
self.mouseInterface = self.drive
self.mouseInterfaceNode = self.mouseInterface.getBottomNode()
self.drive.node().reset()
self.drive.reparentTo(self.mouseWatcher)
# Hookup the drive to the camera
@ -185,6 +187,7 @@ class ShowBase:
self.drive.reparentTo(self.dataUnused)
# Update the mouseInterface to point to the trackball
self.mouseInterface = self.trackball
self.mouseInterfaceNode = self.mouseInterface.getBottomNode()
# Hookup the trackball to the camera
self.trackball.reparentTo(self.mouseWatcher)
self.mouse2cam.reparentTo(self.trackball)