def run(self, command=None): if command != None: if hasattr(command, '__call__'): command(self) else: # Make a suitable environment for running commands if self.entity is not None and self.entity.scene is not None: scene = self.entity.scene() lcls = copy(scene.runEnv) else: lcls = {} lcls['self'] = self lcls['parent'] = self.entity if self.entity is not None and (self.entity.scene is None or scene.isolateEntities): for c,o in self.entity._components.iteritems(): c = str(c) if not c.isdigit(): lcls[c] = o try: exec command in lcls except Exception, ex: error(traceback.format_exc())
def run(self, command=None): if command != None: if hasattr(command, '__call__'): command(self) else: # Make a suitable environment for running commands if self.entity is not None and self.entity.scene is not None: scene = self.entity.scene() lcls = copy(scene.runEnv) else: lcls = {} lcls['self'] = self lcls['parent'] = self.entity if self.entity is not None and (self.entity.scene is None or scene.isolateEntities): for c, o in self.entity._components.iteritems(): c = str(c) if not c.isdigit(): lcls[c] = o try: exec command in lcls except Exception, ex: error(traceback.format_exc())
def entity(self, entity): if self._entity == entity: return if entity == None: # Signal the entity that we are leaving e = self._entity self._entity = None e.remove(self) return # Check that the component is not assigned to another entity if self._entity != None: error( 'Component %s was assigned to entity %s, but it already belongs to %s' % (self, entity, self._entity)) return # Check the entity components to verify that there's not another component with the same id if entity.getComponent(self._id) != None: error('Entity %s already has a component with id %s' % (entity, self._id)) self._entity = entity # If the component is not active, the entity will keep tabs on it but it won't add its properties to itself entity.add(self)
def free(self, **kwargs): """ Release component data here """ if self.released: error('Released %s more than once' % self.id) else: self.tags = [] self.entityTags = [] self.properties = [] self._entity = None self.initialized = False self._data = None self.released = True
def cleanup(self, force = False): #debug('Releasing Data Manager contents %s' % ('(forced)' if force else '',)) keys = [] for url in self.cache.iterkeys(): refCnt = len(gc.get_referrers(self.cache[url])) if force or refCnt <= 1: keys.append(url) if keys: debug( "DataManager will release: %s" % keys) for url in keys: refCnt = len(gc.get_referrers(self.cache[url])) if refCnt > 1: error('Error: Releasing data for %s with ref count: %d' % (url, refCnt)) del self.cache[url]
def cleanup(self, force=False): #debug('Releasing Data Manager contents %s' % ('(forced)' if force else '',)) keys = [] for url in self.cache.iterkeys(): refCnt = len(gc.get_referrers(self.cache[url])) if force or refCnt <= 1: keys.append(url) if keys: debug("DataManager will release: %s" % keys) for url in keys: refCnt = len(gc.get_referrers(self.cache[url])) if refCnt > 1: error('Error: Releasing data for %s with ref count: %d' % (url, refCnt)) del self.cache[url]
def init(self, **data): """ Initialize the required external data, take into account that this function may be called more than once if initialization fails """ from ignifuga.components.Component import Component if not self._initialComponents and 'components' in self._data: if isinstance(self._data['components'], dict): for c_id, c_data in self._data['components'].iteritems(): c_data['id'] = c_id c_data['entity'] = self self._initialComponents.append(Component.create(**c_data)) elif isinstance(self._data['components'], list): for c_data in self._data['components']: c_data['entity'] = self self._initialComponents.append(Component.create(**c_data)) failcount = {} while self._initialComponents: component = self._initialComponents.pop(0) try: component.init(**data) except Exception, ex: #debug(traceback.format_exc()) # Something failed, try it again later self._initialComponents.append(component) if component not in failcount: failcount[component] = 1 else: failcount[component] += 1 if failcount[component] >= 10: debug( 'Temporarily failed initializing Entity %s because of component %s' % (self.id, component)) debug(traceback.format_exc()) self._initFailCount += 1 if self._initFailCount > 10: self._initFailCount = 0 error( 'Ignoring Entity %s, could not initialize it because of component %s' % (self.id, component)) error(traceback.format_exc()) DONE() return else: failcount[component] = 0 # Allow other entities to initialize, then come back here SKIP()
def init(self,**data): """ Initialize the required external data, take into account that this function may be called more than once if initialization fails """ from ignifuga.components.Component import Component if not self._initialComponents and 'components' in self._data: if isinstance(self._data['components'], dict): for c_id, c_data in self._data['components'].iteritems(): c_data['id'] = c_id c_data['entity'] = self self._initialComponents.append(Component.create(**c_data)) elif isinstance(self._data['components'], list): for c_data in self._data['components']: c_data['entity'] = self self._initialComponents.append(Component.create(**c_data)) failcount = {} while self._initialComponents: component = self._initialComponents.pop(0) try: component.init(**data) except Exception, ex: #debug(traceback.format_exc()) # Something failed, try it again later self._initialComponents.append(component) if component not in failcount: failcount[component] = 1 else: failcount[component] += 1 if failcount[component] >= 10: debug('Temporarily failed initializing Entity %s because of component %s' % (self.id, component)) debug(traceback.format_exc()) self._initFailCount+=1 if self._initFailCount > 10: self._initFailCount = 0 error('Ignoring Entity %s, could not initialize it because of component %s' % (self.id, component)) error(traceback.format_exc()) DONE() return else: failcount[component] = 0 # Allow other entities to initialize, then come back here SKIP()
def getMusic(self, url): if url not in self.cache: if url.startswith('embedded:'): data = Gilbert().getEmbedded(url[9:]) if data != None: self.cache[url] = MixMusic(embedded=data) else: error('Error loading embedded data with id: %s', url) return None else: self.cache[url] = MixMusic(srcURL=join(ROOT_DIR, url)) #if DEBUG and (__LINUX__ or __OSX__ or __MINGW__) watchURL = self._urlToWatchUrl(url) if watchURL not in self.watches: Gilbert().gameLoop.addWatch(watchURL) self.watches.append(watchURL) #endif return self.cache[url]
def free(self): """ This free function exists to break the dependency cycle among entities, components, etc If we wait to do what's done here in __del__ the cycle of dependencies is never broken and the data won't be garbage collected. It should be only called from __del__ or unregister """ if self._released: error("Node %s released more than once" % self.id) self._data = {} self.scene = None for component in self._components.itervalues(): # Mark them not active because some components (like sound) depend on it component.active=False component.free() self._components = {} self._componentsByTag = {} self._properties = {} self._released = True self._initialComponents = []
def free(self): """ This free function exists to break the dependency cycle among entities, components, etc If we wait to do what's done here in __del__ the cycle of dependencies is never broken and the data won't be garbage collected. It should be only called from __del__ or unregister """ if self._released: error("Node %s released more than once" % self.id) self._data = {} self.scene = None for component in self._components.itervalues(): # Mark them not active because some components (like sound) depend on it component.active = False component.free() self._components = {} self._componentsByTag = {} self._properties = {} self._released = True self._initialComponents = []
def add(self, component): """ Add a component to the entity""" if component.id in self._components and self._components[component.id] != component: error('Entity %s already has a different component with id %s' % (self, component.id)) return self._components[component.id] = component if component.entity != self: component.entity = self if component.active: self.addProperties(component) self.addTags(component.entityTags) for tag in component.tags: if tag not in self._componentsByTag: self._componentsByTag[tag] = [] self._componentsByTag[tag].append(component) if self.scene is not None: scene = self.scene() if not scene.isolateEntities and not str(component.id).isdigit(): scene.runEnv[component.id] = component
def entity(self, entity): if self._entity == entity: return if entity == None: # Signal the entity that we are leaving e = self._entity self._entity = None e.remove(self) return # Check that the component is not assigned to another entity if self._entity != None: error('Component %s was assigned to entity %s, but it already belongs to %s' % (self, entity, self._entity)) return # Check the entity components to verify that there's not another component with the same id if entity.getComponent(self._id) != None: error('Entity %s already has a component with id %s' % (entity, self._id)) self._entity = entity # If the component is not active, the entity will keep tabs on it but it won't add its properties to itself entity.add(self)
def add(self, component): """ Add a component to the entity""" if component.id in self._components and self._components[ component.id] != component: error('Entity %s already has a different component with id %s' % (self, component.id)) return self._components[component.id] = component if component.entity != self: component.entity = self if component.active: self.addProperties(component) self.addTags(component.entityTags) for tag in component.tags: if tag not in self._componentsByTag: self._componentsByTag[tag] = [] self._componentsByTag[tag].append(component) if self.scene is not None: scene = self.scene() if not scene.isolateEntities and not str(component.id).isdigit(): scene.runEnv[component.id] = component