资源卸载
资源数据载入后一直驻留在内存中直到到应用程序强制卸载(通过资源组管理器或者直接释放资源)。也可以通过资源组管理器在组的层级上卸载资源,意思是说所有同一组中的资源会被组管理器一同释放。Ogre绝不会自动从内存中释放资源,并且你不能够强制卸载还被资源组引用的资源。
3D应用程序的智能资源管理是一个正在讨论的主题,所以我不能说一个系统好于另外一个。只需要提醒你Ogre不能为你管理你的资源。任何未来的智能资源管理(例如,即时的载入/卸载方式)都必须被开发者支持。幸运的,Ogre允许高度的控制资源的生存周期,象你在这章看到的一样,你可以很容易支持智能的资源管理。
图7-1:资源生存周期示意图
当你决定实现自己的资源内存管理器的话,你就有必要了解上面图中所展示的资源生命期的各种状态,以及它们之间是如何转换的。
·未定义状态:这是在应用程序启动的时候所有资源的默认状态;在资源被定义之前,Ogre是不知道它的,你可以手动使用ResourceGroupManager::declareResource()或者在解析脚本(例如材质脚本)的时候定义资源。在这个状态下,你的资源不使用任何内存。
•已声明状态:当你通知Ogre你要把资源作为要载入内容的一部分(例如,调用ResourceGroupManager::loadResourceGroup())的时候你就需要向系统声明这个资源。在任何时候都可以执行对资源的声明工作(例如通过ResourceGroupManager::declareResource()方法),甚至可以在你的渲染系统初始化之前就把你需要的资源声明出来。这与资源管理器的创建工作不同,对ResourceManager::create()方法的调用一定要在渲染系统的初始化之后才能执行。
·未载入状态:当资源初始化之后就进入了这个状态。资源的初始化可以通过调用ResourceGroupManager::initialiseAllResourceGroups()方法或者ResourceGroupManager:: initialiseResourceGroup()方法来完成,而当你执行Root::initialize()的时候也会附加的帮你把之前所有声明的资源初都进行始化工作。在进入未载入状态之后,资源会使用一小部分的内存,用于存放定义的实例,但是实际资源数据并没有被载入内存。载入状态的资源也可以通过调用ResourceManager::unload(),ResourceManager::unloadAll(),ResourceManager:: unloadAllUnreferencedResources(),ResourceGroupManager::unloadResourceGroup()或者Resource:unload()来释放数据从而转入未载入状态。这些工作虽然不会删除资源的引用,但是真正的数据会被卸载出内存。
•已载入状态:这是你的资源“全部激活”时候的状态:资源的数据(例如,贴图资源中的实际图片数据)在内存中存在,并且可以在你的应用程序中直接使用。当你的应用程序使用它们的时候(例如,使用SceneManager::createEntity()添加一个实体到场景中),如果它们没有被载入(并且资源管理器的内存配额没有超出)Ogre会自动帮你载入它们。当然你也可以手动的调用Resource::load(),Resource::reload(),ResourceManager::load(),ResourceManager::reload(),ResourceManager::reloadAll(),ResourceManager:: reloadAllUnreferencedResources()或者ResourceGroupManager:: loadResourceGroup()等方法来强制载入。