[2.1] correct way to add scene nodes

Problems building or running the engine, queries about how to use features etc.
Post Reply
rrl
Halfling
Posts: 78
Joined: Sun Jun 04, 2017 12:33 am

[2.1] correct way to add scene nodes

Post by rrl »

Ogre Version: 2.1
Operating System: Linux
Render System: GL3PlusRenderer

I don't use the Samples/2.0/Common/... framework because it's setup to be relied upon by a bunch of tutorials, too complex because of that, and just for my app I'd like to make it easier to distribute. Below is a cutdown example of my code which I hope gives the idea of what I'm doing. It's like this because the user opens a file and when I process the file, I then add it as a scene node. I have a few problems here.

In createScene() I've created a static mesh just as is done in APIUsage/DynamicGeometry samples via createStaticMesh() and it returns an Ogre::MeshPtr which I add to a vector. Then immediately after, I add it to the scene as an item. Somehow I don't believe this is correct because in doing this, I've had to do the following two steps.

1) I have a static 'called' flag in createScene(), and it's there because if I don't add it, I'll rightfully get an 'already exists' error for the item as it would be trying to create the item multiple times.

2) I have a similar mesh_loaded flag (in frameRenderingQueued) just to say the user has already selected a file so call createScene() just once to create the scene items, otherwise, it'll shutdown.

This works, kind of, but I know it's not correct and hence my inexperience in all this. Can anyone help out and tell me how this is wrongly structured?

Code: Select all

class QtOgreWindow : public QWindow, public Ogre::FrameListener
{
	// ...
};

void QtOgreWindow::initialize()
{
	Ogre::ConfigFile ...
	registerHlms();
	ogreSceneManager = ...
	ogreCamera = ...
	ogreRoot->addFrameListener(this);
}

void QtOgreWindow::createScene()
{
	static bool called = false;

	Ogre::HlmsManager hlmsManager = ...
	hlmsPbs->createDatablock( ... );
	Ogre::HlmsMacroblock macroblock = ...

	Ogre::MeshPtr mp;
	if (called == false) {
		for ( ; ; ) {
			mp = createStaticMesh();
			meshes.push_back(mp);
		}

		for (auto& m : meshes) {
			Ogre::Item *item = ogreSceneManager->createItem(m, Ogre::SCENE_DYNAMIC);
       			item->setDatablock(block);
       			mSceneNode = ogreSceneManager->getRootSceneNode(Ogre::SCENE_DYNAMIC)->createChildSceneNode(Ogre::SCENE_DYNAMIC);
        	    	mSceneNode->attachObject(item);
        	    	mSceneNode->setPosition(Ogre::Vector3(0.0f, 0.0f, 0.0f));
        	    	mSceneNode->setScale(Ogre::Vector3(2.0f, 2.0f, 2.0f));
		}
	}	
}

QtOgreWindow::frameRenderingQueued(const Ogre::FrameEvent& evt)
{
	if (mesh_loaded)
		createScene();

	return true;
}
Last edited by rrl on Sun Jun 24, 2018 1:26 am, edited 2 times in total.
User avatar
dark_sylinc
OGRE Team Member
OGRE Team Member
Posts: 5296
Joined: Sat Jul 21, 2007 4:55 pm
Location: Buenos Aires, Argentina
x 1278
Contact:

Re: [2.1] correct way to add scene nodes

Post by dark_sylinc »

1. I strongly suggest you compile for Debug (If you're using CMake, set CMAKE_BUILD_TYPE to "Debug" no quotes; ensure DEBUG is defined, else just append -DDEBUG=1 to CMAKE_CXX_FLAGS_DEBUG)
This will give you additional asserts and verifications, as well as giving you readable names out of IdString, instead of "[Hash 0x58d8814a]"

2. The error you're getting is because createDatablock got called twice for the same name. It's possible you're calling this function more than once with the same name as argument, or the other possibility is that you have .material or .material.json file defining a material with that same name and you didn't even notice.
A third possibility is that the names are different but there was a hash collision. This is extremely unlikely, but if that's the case, the debug build will catch that.

Cheers
rrl
Halfling
Posts: 78
Joined: Sun Jun 04, 2017 12:33 am

Re: [2.1] correct way to add scene nodes

Post by rrl »

Sorry, I don't think my question is getting across, I already know why I'm getting that error and I thought I explained that. Yes, it's being called twice because the structure of my program is wrong. So I removed it as if you just glance at the post, you'll get the wrong idea. I'll continue editing the OP trying to clarify my question.
Post Reply