From fe79ba9dca8d26ad9b1cbc98e25f181f570dc2a5 Mon Sep 17 00:00:00 2001 From: Roger Hughston Date: Wed, 23 Feb 2005 02:03:00 +0000 Subject: [PATCH] *** empty log message *** --- .../distributed/DistributedSmoothNodeAI.py | 40 ++-- direct/src/ffi/FFIConstants.py | 2 +- direct/src/ffi/FFIExternalObject.py | 22 +- direct/src/ffi/FFIInterrogateDatabase.py | 10 + direct/src/ffi/FFIOverload.py | 14 +- direct/src/ffi/FFISpecs.py | 38 ++- direct/src/ffi/FFITypes.py | 218 +++++++++++++++--- direct/src/interval/IntervalManager.py | 2 +- 8 files changed, 270 insertions(+), 76 deletions(-) diff --git a/direct/src/distributed/DistributedSmoothNodeAI.py b/direct/src/distributed/DistributedSmoothNodeAI.py index fed6ed59c8..6c69aa807e 100755 --- a/direct/src/distributed/DistributedSmoothNodeAI.py +++ b/direct/src/distributed/DistributedSmoothNodeAI.py @@ -23,36 +23,36 @@ class DistributedSmoothNodeAI(DistributedNodeAI.DistributedNodeAI, # These have their FFI functions exposed for efficiency def setSmH(self, h, t): - self._NodePath__overloaded_setH_ptrNodePath_float(h) + self.private__overloaded_setH_ptrNodePath_float(h) def setSmZ(self, z, t): - self._NodePath__overloaded_setZ_ptrNodePath_float(z) + self.private__overloaded_setZ_ptrNodePath_float(z) def setSmXY(self, x, y, t): - self._NodePath__overloaded_setX_ptrNodePath_float(x) - self._NodePath__overloaded_setY_ptrNodePath_float(y) + self.private__overloaded_setX_ptrNodePath_float(x) + self.private__overloaded_setY_ptrNodePath_float(y) def setSmXZ(self, x, z, t): - self._NodePath__overloaded_setX_ptrNodePath_float(x) - self._NodePath__overloaded_setZ_ptrNodePath_float(z) + self.private__overloaded_setX_ptrNodePath_float(x) + self.private__overloaded_setZ_ptrNodePath_float(z) def setSmPos(self, x, y, z, t): - self._NodePath__overloaded_setPos_ptrNodePath_float_float_float(x,y,z) + self.private__overloaded_setPos_ptrNodePath_float_float_float(x,y,z) def setSmHpr(self, h, p, r, t): - self._NodePath__overloaded_setHpr_ptrNodePath_float_float_float(h,p,r) + self.private__overloaded_setHpr_ptrNodePath_float_float_float(h,p,r) def setSmXYH(self, x, y, h, t): - self._NodePath__overloaded_setX_ptrNodePath_float(x) - self._NodePath__overloaded_setY_ptrNodePath_float(y) - self._NodePath__overloaded_setH_ptrNodePath_float(h) + self.private__overloaded_setX_ptrNodePath_float(x) + self.private__overloaded_setY_ptrNodePath_float(y) + self.private__overloaded_setH_ptrNodePath_float(h) def setSmXYZH(self, x, y, z, h, t): - self._NodePath__overloaded_setPos_ptrNodePath_float_float_float(x,y,z) - self._NodePath__overloaded_setH_ptrNodePath_float(h) + self.private__overloaded_setPos_ptrNodePath_float_float_float(x,y,z) + self.private__overloaded_setH_ptrNodePath_float(h) def setSmPosHpr(self, x, y, z, h, p, r, t): - self._NodePath__overloaded_setPosHpr_ptrNodePath_float_float_float_float_float_float(x,y,z,h,p,r) + self.private__overloaded_setPosHpr_ptrNodePath_float_float_float_float_float_float(x,y,z,h,p,r) def clearSmoothing(self, bogus = None): pass @@ -60,16 +60,16 @@ class DistributedSmoothNodeAI(DistributedNodeAI.DistributedNodeAI, # Do we use these on the AIx? def setComponentX(self, x): - self._NodePath__overloaded_setX_ptrNodePath_float(x) + self.private__overloaded_setX_ptrNodePath_float(x) def setComponentY(self, y): - self._NodePath__overloaded_setY_ptrNodePath_float(y) + self.private__overloaded_setY_ptrNodePath_float(y) def setComponentZ(self, z): - self._NodePath__overloaded_setZ_ptrNodePath_float(z) + self.private__overloaded_setZ_ptrNodePath_float(z) def setComponentH(self, h): - self._NodePath__overloaded_setH_ptrNodePath_float(h) + self.private__overloaded_setH_ptrNodePath_float(h) def setComponentP(self, p): - self._NodePath__overloaded_setP_ptrNodePath_float(p) + self.private__overloaded_setP_ptrNodePath_float(p) def setComponentR(self, r): - self._NodePath__overloaded_setR_ptrNodePath_float(r) + self.private__overloaded_setR_ptrNodePath_float(r) def setComponentT(self, t): pass diff --git a/direct/src/ffi/FFIConstants.py b/direct/src/ffi/FFIConstants.py index 1ace18472e..e5fb7f010f 100644 --- a/direct/src/ffi/FFIConstants.py +++ b/direct/src/ffi/FFIConstants.py @@ -21,4 +21,4 @@ InterrogateModuleName = None wantComments = 1 # Should FFI output type assertions? -wantTypeChecking = 1 +wantTypeChecking = 0 diff --git a/direct/src/ffi/FFIExternalObject.py b/direct/src/ffi/FFIExternalObject.py index 6d6da9d8b2..74ee60abaf 100644 --- a/direct/src/ffi/FFIExternalObject.py +++ b/direct/src/ffi/FFIExternalObject.py @@ -1,4 +1,4 @@ - +from new import instance import FFIConstants WrapperClassMap = {} @@ -25,6 +25,23 @@ def registerInTypeMap(pythonClass): WrapperClassMap[typeIndex] = pythonClass +def funcToMethod(func,clas,method_name=None): + """Adds func to class so it is an accessible method; use method_name to specify the name to be used for calling the method. + The new method is accessible to any instance immediately.""" + func.im_class=clas + func.im_func=func + func.im_self=None + if not method_name: + clas.__dict__[method_name]=func + else: + clas.__dict__[func.__name__]=func + + +def FFIInstance(classdef, this = 0, userManagesMemory = 0 ): + answer = instance(classdef) + answer.this = this + answer.userManagesMemory = userManagesMemory + return answer class FFIExternalObject: def __init__(self, *_args): @@ -130,7 +147,8 @@ class FFIExternalObject: # We do not need to downcast if we already have the same class if (exactWrapperClass and (exactWrapperClass != self.__class__)): # Create a new wrapper class instance - exactObject = exactWrapperClass(None) + #exactObject = exactWrapperClass(None) + exactObject = FFIInstance(exactWrapperClass) # Get the downcast pointer that has had all the downcast # funcs called downcastObject = self.downcast(exactWrapperClass) diff --git a/direct/src/ffi/FFIInterrogateDatabase.py b/direct/src/ffi/FFIInterrogateDatabase.py index fbbfb27c0e..689bf6a69b 100644 --- a/direct/src/ffi/FFIInterrogateDatabase.py +++ b/direct/src/ffi/FFIInterrogateDatabase.py @@ -52,6 +52,8 @@ def outputGlobalFileImports(file, methodList, CModuleName): # Import Python's builtin types file.write('from types import IntType, LongType, FloatType, NoneType, StringType\n') + file.write('from direct.ffi import FFIExternalObject\n') + # Import the C modules CModuleList = [] @@ -88,6 +90,7 @@ def outputGlobalFileImports(file, methodList, CModuleName): for moduleName in moduleList: if moduleName: file.write('import ' + moduleName + '\n') + file.write('import ' + moduleName + '1\n') file.write('\n') @@ -140,6 +143,13 @@ def outputImportFileImports(file, typeList, CModuleName): file.write('import ' + moduleName + '\n') file.write('\n') + file.write('# Import classes2\n') + for moduleName in moduleList: + if moduleName: + file.write('import ' + moduleName + '1\n') + file.write('\n') + + file.write('# Import the global module file into our name space\n') file.write('from ' + CModuleName + 'Globals import *\n') file.write('\n') diff --git a/direct/src/ffi/FFIOverload.py b/direct/src/ffi/FFIOverload.py index 4415958e2b..8de9392ad4 100644 --- a/direct/src/ffi/FFIOverload.py +++ b/direct/src/ffi/FFIOverload.py @@ -223,10 +223,10 @@ class FFIMethodArgumentTreeCollection: # Global functions do not need static versions if (self.methodSpecList[0].isStatic() and (not self.methodSpecList[0].isConstructor())): - indent(file, nesting+1, 'def ' + + indent(file, nesting, 'def ' + self.methodSpecList[0].name + '(*_args):\n') else: - indent(file, nesting+1, 'def ' + + indent(file, nesting, 'def ' + self.methodSpecList[0].name + '(self, *_args):\n') self.methodSpecList[0].outputCFunctionComment(file, nesting+2) indent(file, nesting+2, 'numArgs = len(_args)\n') @@ -239,17 +239,25 @@ class FFIMethodArgumentTreeCollection: # Constructors are not treated as static. They are special because # they are not really constructors, they are instance methods that fill # in the this pointer. + methodName = self.methodSpecList[0].name if (self.methodSpecList[0].isStatic() and (not self.methodSpecList[0].isConstructor()) and (not isinstance(self.methodSpecList[0], FFISpecs.GlobalFunctionSpecification))): self.outputOverloadedStaticFooter(file, nesting) + else: + if self.classTypeDesc : + indent(file, nesting, "FFIExternalObject.funcToMethod("+methodName+','+ self.classTypeDesc.foreignTypeName+ ",'"+methodName+"')\n") + indent(file, nesting, 'del '+methodName+'\n') + indent(file, nesting, ' \n') + indent(file, nesting+1, '\n') def outputOverloadedStaticFooter(self, file, nesting): # foo = staticmethod(foo) methodName = self.methodSpecList[0].name - indent(file, nesting+1, methodName + ' = staticmethod(' + methodName + ')\n') + indent(file, nesting, self.classTypeDesc.foreignTypeName + '.' + methodName + ' = staticmethod(' + methodName + ')\n') + indent(file, nesting,'del ' +methodName+' \n\n') def setup(self): for method in self.methodSpecList: diff --git a/direct/src/ffi/FFISpecs.py b/direct/src/ffi/FFISpecs.py index b702d50cdc..e583bb61e0 100644 --- a/direct/src/ffi/FFISpecs.py +++ b/direct/src/ffi/FFISpecs.py @@ -86,7 +86,7 @@ class FunctionSpecification: So "getChild(int)" becomes "overloaded_getChild_int(int)" """ if self.overloaded: - name = '__overloaded_' + self.name + name = 'private__overloaded_' + self.name for methodArgSpec in self.typeDescriptor.argumentTypes: name = name + '_' + methodArgSpec.typeDescriptor.foreignTypeName return name @@ -186,6 +186,8 @@ class GlobalFunctionSpecification(FunctionSpecification): if (i < (len(argTypes)-1)): file.write(', ') file.write(')\n') + #indent(file,1, 'if returnValue is None:\n') + #indent(file,2, 'return None\n') returnType = self.typeDescriptor.returnType.recursiveTypeDescriptor() returnType.generateReturnValueWrapper(None, file, self.typeDescriptor.userManagesMemory, @@ -199,7 +201,7 @@ class GlobalFunctionSpecification(FunctionSpecification): ################################################## def outputMethodHeader(self, methodClass, file, nesting): argTypes = self.typeDescriptor.argumentTypes - indent(file, nesting+1, 'def ' + self.getFinalName() + '(') + indent(file, nesting, 'def ' + self.getFinalName() + '(') for i in range(len(argTypes)): # Instead of the first argument, put self if (i == 0): @@ -229,6 +231,9 @@ class GlobalFunctionSpecification(FunctionSpecification): if (i < (len(argTypes)-1)): file.write(', ') file.write(')\n') + indent(file,1, 'if returnValue is None:\n') + indent(file,2, 'return None\n') + returnType = self.typeDescriptor.returnType.recursiveTypeDescriptor() returnType.generateReturnValueWrapper(methodClass, file, self.typeDescriptor.userManagesMemory, @@ -288,12 +293,13 @@ class MethodSpecification(FunctionSpecification): if (i < (len(thislessArgTypes)-1)): file.write(', ') file.write('):\n') + self.outputCFunctionComment(file, nesting+2) + def outputConstructorBody(self, methodClass, file, nesting): # The method body will look something like # self.this = panda.Class_constructor(arg) # self.userManagesMemory = 1 (optional) - self.outputCFunctionComment(file, nesting+2) argTypes = self.typeDescriptor.argumentTypes thislessArgTypes = self.typeDescriptor.thislessArgTypes() self.outputTypeChecking(methodClass, thislessArgTypes, file, nesting+2) @@ -327,11 +333,11 @@ class MethodSpecification(FunctionSpecification): if (i < (len(thislessArgTypes)-1)): file.write(', ') file.write('):\n') + self.outputCFunctionComment(file, nesting+2) def outputDestructorBody(self, methodClass, file, nesting): # The method body will look something like # panda.Class_destructor(self.this) - self.outputCFunctionComment(file, nesting+2) functionName = (self.typeDescriptor.moduleName + '.' + self.typeDescriptor.wrapperName) # Make sure the module and function have not been deleted first @@ -349,7 +355,7 @@ class MethodSpecification(FunctionSpecification): def outputMethodHeader(self, methodClass, file, nesting): argTypes = self.typeDescriptor.argumentTypes thislessArgTypes = self.typeDescriptor.thislessArgTypes() - indent(file, nesting+1, 'def ' + self.getFinalName() + '(self') + indent(file, nesting, 'def ' + self.getFinalName() + '(self') if (len(thislessArgTypes) > 0): file.write(', ') for i in range(len(thislessArgTypes)): @@ -376,7 +382,7 @@ class MethodSpecification(FunctionSpecification): file.write(thislessArgTypes[i].passName()) if (i < (len(thislessArgTypes)-1)): file.write(', ') - file.write(')\n') + file.write(')\n') # If this is an augmented assignment operator like +=, we have special rules # In this case we simply call the C++ function, make sure we got the same # return value back, then return self. Otherwise if you let it go through the @@ -392,6 +398,12 @@ class MethodSpecification(FunctionSpecification): needsDowncast, nesting+2) def outputMethodFooter(self, methodClass, file, nesting): + indent(file, nesting, 'FFIExternalObject.funcToMethod(' +self.getFinalName()+ ',' + methodClass.foreignTypeName + ",'" +self.getFinalName() +"')\n") + indent(file, nesting, 'del ' + self.getFinalName()+' \n') + indent(file, nesting+1,'\n') + #indent(file, nesting,methodClass.foreignTypeName +'.'+ self.getFinalName() + ' = staticmethod(' + self.getFinalName() + ')\n') + #indent(file, nesting,'del ' + self.getFinalName()+' \n') + #indent(file, nesting+1, '\n') indent(file, nesting+1, '\n') @@ -400,12 +412,13 @@ class MethodSpecification(FunctionSpecification): ################################################## def outputStaticHeader(self, methodClass, file, nesting): argTypes = self.typeDescriptor.argumentTypes - indent(file, nesting+1, 'def ' + self.getFinalName() + '(') + indent(file, nesting, 'def ' + self.getFinalName() + '(') for i in range(len(argTypes)): file.write(argTypes[i].name) if (i < (len(argTypes)-1)): file.write(', ') - file.write('):\n') + file.write('):\n') + def outputStaticBody(self, methodClass, file, nesting): # The method body will look something like @@ -431,7 +444,8 @@ class MethodSpecification(FunctionSpecification): 1, nesting+2) def outputStaticFooter(self, methodClass, file, nesting): - indent(file, nesting+1, self.getFinalName() + ' = staticmethod(' + self.getFinalName() + ')\n') + indent(file, nesting,methodClass.foreignTypeName +'.'+ self.getFinalName() + ' = staticmethod(' + self.getFinalName() + ')\n') + indent(file, nesting,'del ' + self.getFinalName()+' \n') indent(file, nesting+1, '\n') ################################################## @@ -440,7 +454,7 @@ class MethodSpecification(FunctionSpecification): def outputInheritedMethodHeader(self, methodClass, parentList, file, nesting, needsDowncast): argTypes = self.typeDescriptor.argumentTypes thislessArgTypes = self.typeDescriptor.thislessArgTypes() - indent(file, nesting+1, 'def ' + self.getFinalName() + '(self') + indent(file, nesting, 'def ' + self.getFinalName() + '(self') if (len(thislessArgTypes) > 0): file.write(', ') for i in range(len(thislessArgTypes)): @@ -492,7 +506,9 @@ class MethodSpecification(FunctionSpecification): needsDowncast, nesting+2) def outputInheritedMethodFooter(self, methodClass, parentList, file, nesting, needsDowncast): - indent(file, nesting+1, '\n') + indent(file, nesting, 'FFIExternalObject.funcToMethod(' +self.getFinalName()+ ',' + methodClass.foreignTypeName + ",'" +self.getFinalName() +"')\n") + indent(file, nesting, 'del ' + self.getFinalName()+' \n') + indent(file, nesting+1,'\n') class GlobalValueSpecification: diff --git a/direct/src/ffi/FFITypes.py b/direct/src/ffi/FFITypes.py index ed1a94af1b..dacb19837d 100644 --- a/direct/src/ffi/FFITypes.py +++ b/direct/src/ffi/FFITypes.py @@ -507,18 +507,27 @@ class ClassTypeDescriptor(BaseTypeDescriptor): passed in. """ fileName = self.foreignTypeName + '.py' + fileName1 = self.foreignTypeName + '1.py' file = open(os.path.join(dir, fileName), 'w') indent(file, 0, FFIConstants.generatedHeader) self.outputBaseImports(file) - self.generateCode(file, 0) + self.generateCode1(file, 0,extensionsDir) + file.close() + + file = open(os.path.join(dir, fileName1), 'w') + indent(file, 0, FFIConstants.generatedHeader) + #self.outputBaseImports(file) + self.generateCode2(file, 0,extensionsDir,self.foreignTypeName) + file.close() + # Copy in any extensions we may have - self.copyExtensions(extensionsDir, file, 0) - self.outputClassFooter(file) + #self.copyExtensions(extensionsDir, file, 0) + #self.outputClassFooter(file) file.close() - def generateCode(self, file, nesting): + def generateCode(self, file, nesting, extensionsDir=None): self.recordOverloadedMethods() self.cullOverloadedMethods() @@ -551,6 +560,115 @@ class ClassTypeDescriptor(BaseTypeDescriptor): self.destructor.generateDestructorCode(self, file, nesting) # If you have no destructor, inherit one + ########################## + ## Extension methods moved up locally + if extensionsDir : + self.copyExtensions(extensionsDir, file, 0) + + ########################## + ## import return types + returnTypeModules = self.getReturnTypeModules() + if len(returnTypeModules): + for moduleName in returnTypeModules: + indent(file, nesting, 'import ' + moduleName + '\n') + + ################################ + + + if len(self.staticMethods): + indent(file, nesting+1, '\n') + indent(file, nesting+1, '##################################################\n') + indent(file, nesting+1, '# Static Methods #\n') + indent(file, nesting+1, '##################################################\n') + indent(file, nesting+1, '\n') + for method in self.staticMethods: + method.generateStaticCode(self, file, nesting) + + if len(self.instanceMethods): + indent(file, nesting+1, '\n') + indent(file, nesting+1, '##################################################\n') + indent(file, nesting+1, '# Instance methods #\n') + indent(file, nesting+1, '##################################################\n') + indent(file, nesting+1, '\n') + for method in self.instanceMethods: + method.generateMethodCode(self, file, nesting) + + if len(self.upcastMethods): + indent(file, nesting+1, '\n') + indent(file, nesting+1, '##################################################\n') + indent(file, nesting+1, '# Upcast methods #\n') + indent(file, nesting+1, '##################################################\n') + indent(file, nesting+1, '\n') + for method in self.upcastMethods: + method.generateUpcastMethodCode(self, file, nesting) + + if len(self.downcastMethods): + indent(file, nesting+1, '\n') + indent(file, nesting+1, '##################################################\n') + indent(file, nesting+1, '# Downcast methods #\n') + indent(file, nesting+1, '##################################################\n') + indent(file, nesting+1, '\n') + for method in self.downcastMethods: + method.generateDowncastMethodCode(self, file, nesting) + + # Copy in all our parent nodes (only does work if we are an MI node) + self.copyParentMethods(file, nesting) + + self.generateOverloadedMethods(file, nesting) + + def generateCode1(self, file, nesting, extensionsDir=None): + + self.recordOverloadedMethods() + self.cullOverloadedMethods() + self.outputImports(file, nesting) + self.outputClassHeader(file, nesting) + self.outputClassComment(file, nesting) + self.outputClassCModules(file, nesting) + + self.outputNestedTypes(file, nesting) + + indent(file, nesting+1, '\n') + indent(file, nesting+1, '##################################################\n') + indent(file, nesting+1, '# Constructors #\n') + indent(file, nesting+1, '##################################################\n') + indent(file, nesting+1, '\n') + self.outputBaseConstructor(file, nesting) + if self.constructors: + for method in self.constructors: + method.generateConstructorCode(self, file, nesting) + else: + self.outputEmptyConstructor(file, nesting) + + indent(file, nesting+1, '\n') + indent(file, nesting+1, '##################################################\n') + indent(file, nesting+1, '# Destructor #\n') + indent(file, nesting+1, '##################################################\n') + indent(file, nesting+1, '\n') + self.outputBaseDestructor(file, nesting) + if self.destructor: + self.destructor.generateDestructorCode(self, file, nesting) + # If you have no destructor, inherit one + ########################## + ## Extension methods moved up locally + if extensionsDir : + self.copyExtensions(extensionsDir, file, 0) + + + + def generateCode2(self, file, nesting, extensionsDir, file1module): + + indent(file, nesting, 'from ' + file1module + ' import *\n') + + ########################## + ## import return types + returnTypeModules = self.getReturnTypeModules() + if len(returnTypeModules): + for moduleName in returnTypeModules: + indent(file, nesting, 'import ' + moduleName + '\n') + + ################################ + + if len(self.staticMethods): indent(file, nesting+1, '\n') indent(file, nesting+1, '##################################################\n') @@ -632,6 +750,7 @@ class ClassTypeDescriptor(BaseTypeDescriptor): indent(file, 0, '# CMODULE [' + self.moduleName + ']\n') # Everybody imports types for type checking indent(file, 0, 'from types import IntType, LongType, FloatType, NoneType, StringType\n') + indent(file, 0, 'from direct.ffi import FFIExternalObject\n') indent(file, 0, '\n') indent(file, 0, '# Import all the C modules this class uses\n') @@ -641,6 +760,7 @@ class ClassTypeDescriptor(BaseTypeDescriptor): indent(file, 0, 'import ' + moduleName + 'Downcasts\n') indent(file, 0, '\n') indent(file, 0, 'from direct.ffi import FFIExternalObject\n') + def outputImportsRecursively(self, parent, file, nesting): @@ -750,10 +870,10 @@ class ClassTypeDescriptor(BaseTypeDescriptor): # Store the class C modules for the class so they do not # get garbage collected before we do # TODO: this did not appear to work so I'm taking it out - # indent(file, nesting+1, '__CModules__ = [') - # for moduleName in self.getCModules(): + #indent(file, nesting+1, '__CModules__ = [') + #for moduleName in self.getCModules(): # file.write(moduleName + ',') - # file.write(']\n') + #file.write(']\n') # Store the downcast function modules so the FFIExternalObject # can index into them to find the downcast functions @@ -780,14 +900,18 @@ class ClassTypeDescriptor(BaseTypeDescriptor): """ indent(file, nesting+1, 'def __init__(self, *_args):\n') - indent(file, nesting+2, '# Initialize the super class\n') - indent(file, nesting+2, 'FFIExternalObject.FFIExternalObject.__init__(self)\n') - indent(file, nesting+2, '# If you want an empty shadow object, pass in None\n') - indent(file, nesting+2, 'if ((len(_args) == 1) and (_args[0] == None)):\n') - indent(file, nesting+3, 'return\n') - indent(file, nesting+2, '# Otherwise, call the C constructor\n') + indent(file, nesting+2, '# Do Not Initialize the super class it is inlined\n') + #indent(file, nesting+2, '# Initialize the super class\n') + #indent(file, nesting+2, 'FFIExternalObject.FFIExternalObject.__init__(self)\n') + ## this is not the right way to do this any more.. + indent(file, nesting+2, '# If you want an empty shadow object use the FFIInstance(class) function\n') + #indent(file, nesting+2, 'if ((len(_args) == 1) and (_args[0] == None)):\n') + #indent(file, nesting+3, 'return\n') + #indent(file, nesting+2, '# Otherwise, call the C constructor\n') indent(file, nesting+2, 'self.constructor(*_args)\n') - indent(file, nesting+2, '\n') + indent(file, nesting, '\n') + + def outputEmptyConstructor(self, file, nesting): @@ -806,20 +930,24 @@ class ClassTypeDescriptor(BaseTypeDescriptor): Python object is garbage collected. We are going to overwrite it with special cleanup for Panda. """ - indent(file, nesting+1, 'def __del__(self):\n') + if self.destructor: + indent(file, nesting+1, 'def __del__(self):\n') - # Reference counting is now handled in the C++ code - # indent(file, nesting+2, 'if isinstance(self, ReferenceCount):\n') - # indent(file, nesting+3, 'self.unref()\n') - # indent(file, nesting+3, 'if (self.getCount() == 0):\n') - # indent(file, nesting+4, 'self.destructor()\n') + # Reference counting is now handled in the C++ code + # indent(file, nesting+2, 'if isinstance(self, ReferenceCount):\n') + # indent(file, nesting+3, 'self.unref()\n') + # indent(file, nesting+3, 'if (self.getCount() == 0):\n') + # indent(file, nesting+4, 'self.destructor()\n') - # If the scripting language owns the memory for this object, - # we need to call the C++ destructor when Python frees the - # shadow object, but only if the userManagesMemory flag is set. - # Also make sure we are not destructing a null pointer - indent(file, nesting+2, 'if (self.userManagesMemory and (self.this != 0)):\n') - indent(file, nesting+3, 'self.destructor()\n') + # If the scripting language owns the memory for this object, + # we need to call the C++ destructor when Python frees the + # shadow object, but only if the userManagesMemory flag is set. + # Also make sure we are not destructing a null pointer + indent(file, nesting+2, 'if (self.userManagesMemory and (self.this != 0)):\n') + self.destructor.outputDestructorBody(self, file, nesting+1) + indent(file, nesting, '\n') + + #indent(file, nesting+3, 'self.destructor()\n') def outputEmptyDestructor(self, file, nesting): @@ -839,27 +967,41 @@ class ClassTypeDescriptor(BaseTypeDescriptor): class destructor with None as the only parameter to get an empty shadow object. """ - if classTypeDesc != self: - indent(file, nesting, 'import ' + self.foreignTypeName + '\n') - indent(file, nesting, 'returnObject = ') + #if classTypeDesc != self: + # indent(file, nesting, 'import ' + self.foreignTypeName + '\n') + indent(file,nesting, 'if returnValue == 0: return None\n') # Do not put Class.Class if this file is the file that defines Class # Also check for nested classes. They do not need the module name either typeName = FFIOverload.getTypeName(classTypeDesc, self) - file.write(typeName) - file.write('(None)\n') - indent(file, nesting, 'returnObject.this = returnValue\n') + #file.write(typeName + '(None)\n') + ### inline the old constructers + + #indent(file, nesting, 'returnObject = ') + #file.write('FFIExternalObject.FFIInstance('+ typeName + ',returnValue,'+str(userManagesMemory)+')\n') + #indent(file,nesting, 'returnObject.this = 0\n'); + #indent(file,nesting, 'returnObject.userManagesMemory = 0\n'); + + ## + #indent(file, nesting, 'returnObject.this = returnValue\n') # Zero this pointers get returned as the Python None object - indent(file, nesting, 'if (returnObject.this == 0): return None\n') - if userManagesMemory: - indent(file, nesting, 'returnObject.userManagesMemory = 1\n') + #indent(file, nesting, 'if (returnObject.this == 0): return None\n') + #if userManagesMemory: + # indent(file, nesting, 'returnObject.userManagesMemory = 1\n') + #else: + # indent(file, nesting, 'returnObject.userManagesMemory = 0\n') + if needsDowncast: + #indent(file, nesting, 'returnObject = FFIExternalObject.FFIInstance('+ typeName + ',returnValue,'+str(userManagesMemory)+')\n') if (FFIOverload.inheritsFrom(self, TypedObjectDescriptor) or self == TypedObjectDescriptor): - indent(file, nesting, 'return returnObject.setPointer()\n') + #indent(file, nesting, 'return returnObject.setPointer()\n') + indent(file, nesting, 'return FFIExternalObject.FFIInstance('+ typeName + ',returnValue,'+str(userManagesMemory)+').setPointer()\n') else: - indent(file, nesting, 'return returnObject\n') + indent(file, nesting,'return FFIExternalObject.FFIInstance('+ typeName + ',returnValue,'+str(userManagesMemory)+')\n') + #indent(file, nesting, 'return returnObject\n') else: - indent(file, nesting, 'return returnObject\n') + indent(file, nesting,'return FFIExternalObject.FFIInstance('+ typeName + ',returnValue,'+str(userManagesMemory)+')\n') + #indent(file, nesting, 'return returnObject\n') diff --git a/direct/src/interval/IntervalManager.py b/direct/src/interval/IntervalManager.py index 231f8009d7..9774453436 100644 --- a/direct/src/interval/IntervalManager.py +++ b/direct/src/interval/IntervalManager.py @@ -18,7 +18,7 @@ class IntervalManager(CIntervalManager): # CIntervalManager object. if globalPtr: - CIntervalManager.__init__(self, None) + #CIntervalManager.__init__(self, None) cObj = CIntervalManager.getGlobalPtr() self.this = cObj.this self.userManagesMemory = 0