forum.boolean.name

forum.boolean.name (http://forum.boolean.name/index.php)
-   Ogre3D (http://forum.boolean.name/forumdisplay.php?f=156)
-   -   помогите разобраться с удалением объектов (http://forum.boolean.name/showthread.php?t=15815)

HolyDel 08.11.2011 22:13

помогите разобраться с удалением объектов
 
Код:

// I will use std::auto_ptr so I need to include 'memory'.
// If you don't know std::auto_ptr, you should check some C++ tutorials/lesson on this matter.
#include <memory>
// I will check for std::exception. If you don't know what exception/try/catch means, you should learn C++ first.
#include <exception>
 
// These are some files that we need to include to use Ogre3D. Note that you can at the beginnings use directly "Ogre.h", to include lots of commonly used classes.
#include "OgreRoot.h"
#include "OgreRenderWindow.h"
#include "OgreWindowEventUtilities.h"
#include "OgreEntity.h"
#include "OgreMaterial.h"
#include "OgreMaterialManager.h"
//Here I include my other files, like the one for SimpleOgreInit...
#include "SimpleOgreInit.h"
 
#include "EasyDefines.h"
#include <cmath>
#include <cstdlib>

Ogre::SceneManager* lScene = 0;
Ogre::SceneNode* lRootSceneNode = 0;

class TempraryObject
{
public:
        Ogre::SceneNode *node;
        Ogre::Entity* entity;
        int lifetime;
        bool free;

        void process()
        {
                lifetime--;
                int lt = lifetime;

                if(lifetime<0 && node !=0 && entity != 0)
                {
//                        node->detachAllObjects();
                        lRootSceneNode->removeChild(node);
//                        lScene->destroySceneNode(node);
       
                        node = 0;
                        entity = 0;
                               
                }
                free = (lifetime<0);
        }
};

void AnOgreApplication()
{
        // I construct my object that will allow me to initialise Ogre easily.
        OgreEasy::SimpleOgreInit lOgreInit;
 
        if(!lOgreInit.initOgre())
        {
                std::cout<<"Impossible to init Ogre correctly."<<std::endl;
                return;
        }
 
        //I prefer to be able to access my variables directly.
        Ogre::Root* lRoot = lOgreInit.mRoot.get();
        Ogre::RenderWindow* lWindow = lOgreInit.mWindow;
 

        lScene = lRoot->createSceneManager(Ogre::ST_GENERIC, "MyFirstSceneManager");
 
        lRootSceneNode = lScene->getRootSceneNode();
 
        // I create a camera. It represent a 'point of view' in the scene.
        Ogre::Camera* lCamera = lScene->createCamera("MyFirstCamera");
 
        // I attach the camera to a new SceneNode. It will be easier then to move it in the scene.
        Ogre::SceneNode* lCameraNode = lRootSceneNode->createChildSceneNode("MyFirstCameraNode");
        lCameraNode->attachObject(lCamera);
 
        float lViewportWidth = 1.0f;
        float lViewportHeight = 1.0f;
        float lViewportLeft        = (1.0f - lViewportWidth) * 0.5f;
        float lViewportTop = (1.0f - lViewportHeight) * 0.5f;
        unsigned short lMainViewportZOrder = 100;
        Ogre::Viewport * vp = lWindow->addViewport(lCamera, lMainViewportZOrder, lViewportLeft, lViewportTop, lViewportWidth, lViewportHeight);
       
        // I want the viewport to draw the scene automatically
        // when I will call lWindow->update();
        vp->setAutoUpdated(true);
 
        // I choose a color for this viewport.
        // I prefer to have a bright color, to detect holes in geometry etc...
        vp->setBackgroundColour(Ogre::ColourValue(0.2,0.2,0.2));
 
        // I choose the visual ratio of the camera. To make it looks real, I want it the same as the viewport.
        float ratio = float(vp->getActualWidth()) / float(vp->getActualHeight());
        lCamera->setAspectRatio(ratio);
 
        // I choose the clipping far& near planes. if far/near>2000, you can get z buffer problem.
        // eg : far/near = 10000/5 = 2000 . it's ok.
        // If (far/near)>2000 then you will likely get 'z fighting' issues.
        lCamera->setNearClipDistance(15.0f);
        lCamera->setFarClipDistance(5000.0f);
 
        // I want my window to be active
        lWindow->setActive(true);
 
        // I want to update myself the content of the window, not automatically.
        lWindow->setAutoUpdated(false);
 
        lRoot->clearEventTimes();
 

        Ogre::String lNameOfResourceGroup = "SHARED";

        Ogre::ResourceGroupManager& lRgMgr = Ogre::ResourceGroupManager::getSingleton();
        lRgMgr.createResourceGroup(lNameOfResourceGroup);
 
        Ogre::String lDirectoryToLoad = "../media";
        bool lIsRecursive = false;
        lRgMgr.addResourceLocation(lDirectoryToLoad, "FileSystem", lNameOfResourceGroup, lIsRecursive);
 
        // The function 'initialiseResourceGroup' parses scripts if any in the locations.
        lRgMgr.initialiseResourceGroup(lNameOfResourceGroup);
 
        // Files that can be loaded are loaded.
        lRgMgr.loadResourceGroup(lNameOfResourceGroup);
 
        // Now the loaded Mesh is available from its ResourceGroup,
        // as well as from the Ogre::MeshManager. A shared pointer to
        // it can be accessed by : Ogre::MeshManager::getSingleton().getByName(name_of_the_mesh);
 
        // Now I can create Entities using that mesh.
        Ogre::String lNameOfTheMesh = "cube.mesh";
        int lNumberOfEntities = 4096;

        float x = - 1500;
        float y = - 900;

        Ogre::MaterialPtr mat = Ogre::MaterialManager::getSingletonPtr()->create("tex1",lNameOfResourceGroup);
        mat->getTechnique(0)->getPass(0)->createTextureUnitState("terrain_texture.jpg");

        float z = 4000;

        std::list<TempraryObject> objects;
        struct process
        {
                void operator()(TempraryObject &obj)
                {
                        obj.process();
                }
        };

        struct pred
        {
                bool operator()(TempraryObject &obj)
                {
                        return obj.free;
                }
        };       

        unsigned long uuid =0;

        while(!lOgreInit.mWindow->isClosed())
        {
                int cadd = (rand() % 20) + 30;
                for(int i=0;i<cadd;++i)
                {
                        uuid++;

                        TempraryObject temp;

                        temp.entity = lScene->createEntity(lNameOfTheMesh);
                        temp.entity->setMaterial(mat);
                        // Now I attach it to a scenenode, so that it becomes present in the scene.
                        char buff[80];
                        itoa(uuid,buff,10);

                        temp.node = lRootSceneNode->createChildSceneNode(buff);
                        temp.node->attachObject(temp.entity);

                        temp.node->translate(float(rand() % 10000 - 5000) * 0.33, float(rand() % 10000 - 5000) * 0.33, float(rand() % 1000 - 500) * 0.33);
                        temp.node->scale(0.1,0.1,0.1);
                        temp.free = false;
                        temp.lifetime = 10 + (rand() % 10);
                       
                        objects.push_back(temp);
                }

                std::for_each(objects.begin(),objects.end(),process());
                std::remove_if(objects.begin(),objects.end(),pred());

                if(GetAsyncKeyState(VK_UP))
                {
                        z -= 10;
                }

                if(GetAsyncKeyState(VK_DOWN))
                {
                        z += 10;
                }

                lCameraNode->setPosition(0,0,z);

                lWindow->update(false);
 
                bool lVerticalSynchro = false;
                lWindow->swapBuffers(lVerticalSynchro);
 
                lRoot->renderOneFrame();
 
                Ogre::WindowEventUtilities::messagePump();
        }
        return;
}
 
int main()
{
        try
        {
                AnOgreApplication();
                std::cout<<"end of the program"<<std::endl;
        }catch(Ogre::Exception &e)
        {
                MWARNING("!!!!Ogre::Exception!!!!\n" << e.what());
        }catch(std::exception &e)
        {
                MWARNING("!!!!std::exception!!!!\n"<<e.what());
        }
        OgreEasy::waitForUser();
        return 0;
}

ненужные кубики не исчезают окончательно. как правильно удалить ноды и ентити?

Coks 09.11.2011 12:49

Ответ: помогите разобраться с удалением объектов
 
по идее так:
Код:

node->detachAllObjects();
node->removeAllChildren();
lScene->destroySceneNode(node);
lScene->destroyEntity(entity);

нод от родителя автоматически удаляется.


Часовой пояс GMT +4, время: 13:35.

vBulletin® Version 3.6.5.
Copyright ©2000 - 2024, Jelsoft Enterprises Ltd.
Перевод: zCarot