EntityTypeDesc.py 4.6 KB

123456789101112131415161718192021222324252627282930313233343536373839404142434445464748495051525354555657585960616263646566676869707172737475767778798081828384858687888990919293949596979899100101102103104105106107108109110111112113114115116117118119120121122123124125126
  1. """EntityTypeDesc module: contains the EntityTypeDesc class"""
  2. from direct.directnotify import DirectNotifyGlobal
  3. import AttribDesc
  4. from direct.showbase.PythonUtil import mostDerivedLast
  5. class EntityTypeDesc:
  6. """This class is meta-data that describes an Entity type."""
  7. notify = DirectNotifyGlobal.directNotify.newCategory('EntityTypeDesc')
  8. output = None
  9. def __init__(self):
  10. self.__class__.privCompileAttribDescs(self.__class__)
  11. self.attribNames = []
  12. self.attribDescDict = {}
  13. # ordered list of attrib descriptors
  14. attribDescs = self.__class__._attribDescs
  15. # create ordered list of attrib names, dict of attrib name to attribDesc
  16. for desc in attribDescs:
  17. attribName = desc.getName()
  18. self.attribNames.append(attribName)
  19. self.attribDescDict[attribName] = desc
  20. def isConcrete(self):
  21. """ means that entity of this exact type can be created """
  22. return not self.__class__.__dict__.has_key('abstract')
  23. def isPermanent(self):
  24. """ means that entity of this exact type cannot be inserted or
  25. removed in the editor """
  26. return self.__class__.__dict__.has_key('permanent')
  27. def getOutputType(self):
  28. return self.output
  29. def getAttribNames(self):
  30. """ returns ordered list of attribute names for this entity type """
  31. return self.attribNames
  32. def getAttribDescDict(self):
  33. """ returns dict of attribName -> attribDescriptor """
  34. return self.attribDescDict
  35. def getAttribsOfType(self, type):
  36. """returns list of attrib names of the given type"""
  37. names = []
  38. for attribName, desc in self.attribDescDict.items():
  39. if desc.getDatatype() == type:
  40. names.append(attribName)
  41. return names
  42. def privCompileAttribDescs(entTypeClass):
  43. """this compiles an ordered list of attribDescs for the Entity class
  44. passed in. The attribute descriptors describe the properties of each
  45. of the Entity type's attributes"""
  46. # has someone already compiled the info?
  47. if entTypeClass.__dict__.has_key('_attribDescs'):
  48. return
  49. c = entTypeClass
  50. EntityTypeDesc.notify.debug('compiling attrib descriptors for %s' %
  51. c.__name__)
  52. # make sure all of our base classes have their complete list of
  53. # attribDescs
  54. for base in c.__bases__:
  55. EntityTypeDesc.privCompileAttribDescs(base)
  56. # aggregate the attribute descriptors from our direct base classes
  57. blockAttribs = c.__dict__.get('blockAttribs', [])
  58. baseADs = []
  59. bases = list(c.__bases__)
  60. # make sure base-class attribs show up before derived-class attribs
  61. mostDerivedLast(bases)
  62. for base in bases:
  63. for desc in base._attribDescs:
  64. # are we blocking this attribute?
  65. if desc.getName() in blockAttribs:
  66. continue
  67. # make sure we haven't already picked up this attribute
  68. # from an earlier base class
  69. for d in baseADs:
  70. if desc.getName() == d.getName():
  71. EntityTypeDesc.notify.warning(
  72. '%s inherits attrib %s from multiple bases' %
  73. (c.__name__, desc.getName()))
  74. break
  75. else:
  76. baseADs.append(desc)
  77. # now that we have all of the descriptors from our base classes,
  78. # add the descriptors from this class
  79. attribDescs = []
  80. if c.__dict__.has_key('attribs'):
  81. for attrib in c.attribs:
  82. desc = AttribDesc.AttribDesc(*attrib)
  83. # if we picked up an attribute with the same name from a base
  84. # class, this overrides it
  85. for ad in baseADs:
  86. if ad.getName() == desc.getName():
  87. baseADs.remove(ad)
  88. # there ought to be no more than one desc with
  89. # this name from the base classes
  90. assert ad not in baseADs
  91. break
  92. attribDescs.append(desc)
  93. c._attribDescs = baseADs + attribDescs
  94. privCompileAttribDescs = staticmethod(privCompileAttribDescs)
  95. def __str__(self):
  96. return str(self.__class__)
  97. def __repr__(self):
  98. # this is used to produce a hash value
  99. return (str(self.__class__.__dict__.get('type',None))+
  100. str(self.output)+
  101. str(self.attribDescDict))