B3d format and animation

Discuss about anything related to the Irrlicht Engine, or read announcements about any significant features or usage changes.
B@z
Posts: 876
Joined: Thu Jan 31, 2008 5:05 pm
Location: Hungary

Post by B@z »

nobody?
Luke
Admin
Posts: 449
Joined: Fri Jul 14, 2006 7:55 am
Location: Australia
Contact:

Post by Luke »

well how is the weapon following the character slowly, is it animating slowly? lagging one frame behind? or something?
i can connect model to joint, but can i connect joint to joint?
well that's a little tricky, changing the joints parents. you can do it manually (with setPosition and setRotation) or just change it in a modelling program.

adding support for this wouldn't work so well with the shared meshes, and there is not much point.
B@z
Posts: 876
Joined: Thu Jan 31, 2008 5:05 pm
Location: Hungary

Post by B@z »

ohh i see ^^

well... the animation seems like ok, but when i'm walking then it moves slowly..

but the funny thing, that it isn't always... if i change something at the joints place (in the code), it becomes slow, and if i start to use other things (programming, but not the joints), then it becomes good... xD maybe just the debugging?
Luke
Admin
Posts: 449
Joined: Fri Jul 14, 2006 7:55 am
Location: Australia
Contact:

Post by Luke »

but the funny thing, that it isn't always... if i change something at the joints place (in the code), it becomes slow, and if i start to use other things (programming, but not the joints), then it becomes good... xD maybe just the debugging?
try updating the absolute positions after you move the joint.

try calling this function with the main mesh node, just before render

Code: Select all

void UpdateAbsoluteTransformationAndChildren(ISceneNode *Node)
{

	Node->updateAbsolutePosition();
	core::list<ISceneNode*>::ConstIterator it = Node->getChildren().begin();
	for (; it != Node->getChildren().end(); ++it)
	{
		UpdateAbsoluteTransformationAndChildren((*it));
	}

}
B@z
Posts: 876
Joined: Thu Jan 31, 2008 5:05 pm
Location: Hungary

Post by B@z »

oh, it seems working!
thank you!
B@z
Posts: 876
Joined: Thu Jan 31, 2008 5:05 pm
Location: Hungary

Post by B@z »

hello again!
i have a problem (again :D )

i made my character with 6 children..

leg's child is torso
torso's child are left arm, right arm, head
left arm's child is left hand
right arm's child is right hand

i have to seperate it like this..

but i could make it cool, but, the FPS went to 15.. before it was about 100.
if i just using the legs (so don't use the children) it's fine (100 FPS)

my player making source is:

Code: Select all

Player::Player(char *mdl, char* tx)
{
	char path[256] = {0};
	sprintf(path,"%s\\legs.b3d",mdl);

	model = new NewtonModel;
	model->mesh = Game.smgr->getMesh(path);
	model->node = Game.smgr->addAnimatedMeshSceneNode(model->mesh);
	model->node->setMaterialTexture(0,Game.driver->getTexture(tx));

	model->collision = NewtonCreateBox(Game.nWorld,50,50,35,NULL);

	model->body = NewtonCreateBody(Game.nWorld,model->collision);

	int characterID = NewtonMaterialCreateGroupID(Game.nWorld);
   
	NewtonMaterialSetDefaultElasticity (Game.nWorld, Game.levelID, characterID, 0.1f);
	NewtonMaterialSetDefaultFriction (Game.nWorld, Game.levelID, characterID, 10.4f, 10.4f);

	// end of materials

	NewtonBodySetMaterialGroupID (model->body, characterID);


	NewtonBodySetUserData(model->body, model->node);

	NewtonBodySetMassMatrix(model->body,10.0f,150.0f,150.0f,150.0f);
	
	// disable auto freeze management for the player
	NewtonBodySetAutoFreeze (model->body, 0);

	// keep the player always active 
	NewtonWorldUnfreezeBody (Game.nWorld, model->body);

	NewtonBodySetTransformCallback(model->body, PlayerSetMeshTransformEvent);
	NewtonBodySetForceAndTorqueCallback(model->body, PlayerApplyForceAndTorqueEvent);

	matrix4 mat;
	mat.setTranslation(vector3df(300,800,300));
	NewtonBodySetMatrix(model->body, mat.pointer());

	vector3df upDirection (0.0f, 1.0f, 0.0f);
	m_upVector = NewtonConstraintCreateUpVector (Game.nWorld, &upDirection.X, model->body); 

	sprintf(path,"%s\\torso.b3d",mdl);
	torso = Game.smgr->addAnimatedMeshSceneNode(Game.smgr->getMesh(path));

	sprintf(path,"%s\\head.b3d",mdl);
	head = Game.smgr->addAnimatedMeshSceneNode(Game.smgr->getMesh(path));

	sprintf(path,"%s\\larm.b3d",mdl);
	larm = Game.smgr->addAnimatedMeshSceneNode(Game.smgr->getMesh(path));

	sprintf(path,"%s\\rarm.b3d",mdl);
	rarm = Game.smgr->addAnimatedMeshSceneNode(Game.smgr->getMesh(path));

	sprintf(path,"%s\\lhand.b3d",mdl);
	lhand = Game.smgr->addAnimatedMeshSceneNode(Game.smgr->getMesh(path));

	sprintf(path,"%s\\rhand.b3d",mdl);
	rhand = Game.smgr->addAnimatedMeshSceneNode(Game.smgr->getMesh(path));

	jTorso = model->node->getJointNode("torso");
	jHead = torso->getJointNode("head");
	jrArm = torso->getJointNode("rarm");
	jlArm = torso->getJointNode("larm");
	jlHand = larm->getJointNode("lhand");
	jrHand = rarm->getJointNode("rhand");
	
	jTorso->addChild(torso);
	jHead->addChild(head);
	jlArm->addChild(larm);
	jrArm->addChild(rarm);
	jlHand->addChild(lhand);
	jrHand->addChild(rhand);
}
as you can see, i'm using newton just for legs (so the problem isn't the newton i think)

at drawing

Code: Select all

void Player::UpdateJoints()
{
	UpdateAbsoluteTransformationAndChildren(model->node);
}

void CGame::Render()
{
	driver->beginScene(true, true, video::SColor(0,220,220,255));

	player->UpdateJoints();
	// render the scene
	smgr->drawAll();

	driver->endScene();

	// Draw fps counter
	int fps = driver->getFPS();
	if (lastFPS != fps)
	{
		wchar_t tmp[1024];
		swprintf(tmp, 1024, L"Newton Example [fps:%d] [triangles:%d]", 
			fps, driver->getPrimitiveCountDrawn());
		device->setWindowCaption(tmp);
		lastFPS = fps;
	}
}
but if i delete the "updateJoints" it's bad too.. so this isn't the problem too..

why is it so slow?
B@z
Posts: 876
Joined: Thu Jan 31, 2008 5:05 pm
Location: Hungary

Post by B@z »

nobody?
pls help! ><;
hybrid
Admin
Posts: 14143
Joined: Wed Apr 19, 2006 9:20 pm
Location: Oldenburg(Oldb), Germany
Contact:

Post by hybrid »

You can simply remove stuff until the FPS goes up again.
B@z
Posts: 876
Joined: Thu Jan 31, 2008 5:05 pm
Location: Hungary

Post by B@z »

yeah, but if i remove the stuf, only the character's leg can be seen.....
hybrid
Admin
Posts: 14143
Joined: Wed Apr 19, 2006 9:20 pm
Location: Oldenburg(Oldb), Germany
Contact:

Post by hybrid »

That's only for actually detemining the cause of the FPS drop. Of course it should be put back once it's running ok.
B@z
Posts: 876
Joined: Thu Jan 31, 2008 5:05 pm
Location: Hungary

Post by B@z »

ohh i see
i removed everything, just the terrain and the player


if i remove this:

Code: Select all

   jTorso = model->node->getJointNode("torso");
   jHead = torso->getJointNode("head");
   jrArm = torso->getJointNode("rarm");
   jlArm = torso->getJointNode("larm");
   jlHand = larm->getJointNode("lhand");
   jrHand = rarm->getJointNode("rhand"); 
everything is ok (350 FPS)
if i don't remove anything it's 35 FPS

if i remove only the hands, it's 110 FPS

if i remove the arms too, it's 220

remove head it's 270...

so when i remove one joint, the FPS raises... i don't think it's normal... xD
B@z
Posts: 876
Joined: Thu Jan 31, 2008 5:05 pm
Location: Hungary

Post by B@z »

i think it's something with the joint update. if i load the joints, but set the visible false (larm->setVisible(false)), then the FPS is raising...
somebody doesn't have the same problem?
dlangdev
Posts: 1324
Joined: Tue Aug 07, 2007 7:28 pm
Location: Beaverton OR
Contact:

Post by dlangdev »

It's probably related to how the joint/bone matrix calculations are hitting the rendering pipeline.

step-through it using the debugger, you'll probably find something in there.
Image
B@z
Posts: 876
Joined: Thu Jan 31, 2008 5:05 pm
Location: Hungary

Post by B@z »

hi!
i don't get it><;

which part should i debug?
and even if I debug, i don't get where is the FPS drop.. because it's a debugger, so it's much more slower...
or i should get something wrong with the numbers?

i've made a little program, what's just for drawing that model

Code: Select all

#include "irrlicht.h"
using namespace irr;
using namespace core;
using namespace scene;
using namespace video;
using namespace io;
using namespace gui;

IrrlichtDevice *device;
IAnimatedMeshSceneNode *legs;

#pragma comment (lib,"irrlicht.lib")

class MyEventReceiver:public irr::IEventReceiver {
public:
bool OnEvent(const SEvent& event)
{
	if (event.EventType == EET_KEY_INPUT_EVENT)
	{
		vector3df currot;
		switch(event.KeyInput.Key)
		{
		case KEY_KEY_A:
			currot = legs->getRotation();
			currot.Y-=5;
			legs->setRotation(currot);
			break;

		case KEY_KEY_D:
			currot = legs->getRotation();
			currot.Y+=5;
			legs->setRotation(currot);
			break;

		case KEY_ESCAPE:
			device->closeDevice();
			break;
		}
	}
	return false;
}
};

int main(int argc, char* argv[])
{
	IVideoDriver* driver;
	ISceneManager* smgr;
	IGUIEnvironment* guienv;
	ICameraSceneNode *cam;
	u32 lasttick;
	int lastFPS = -1;

	MyEventReceiver event;
	// Init the Irrlicht engine
	device = createDevice(EDT_DIRECT3D9, dimension2d<s32>(640, 480), 16, false, true, false,&event);

	driver = device->getVideoDriver();
	smgr = device->getSceneManager();

	cam = smgr->addCameraSceneNode();
	cam->setPosition(vector3df(0, 50, 0));

	lasttick = 0;

	// add skybox
	smgr->addSkyBoxSceneNode(driver->getTexture("data\\world/irrlicht2_up.jpg"),
							driver->getTexture("data\\world/irrlicht2_dn.jpg"),
							driver->getTexture("data\\world/irrlicht2_lf.jpg"),
							driver->getTexture("data\\world/irrlicht2_rt.jpg"),
							driver->getTexture("data\\world/irrlicht2_ft.jpg"),
							driver->getTexture("data\\world/irrlicht2_bk.jpg"));

	IAnimatedMeshSceneNode *head,*torso,*larm,*rarm,*lhand,*rhand;
	IBoneSceneNode *jTorso, *jHead, *jrArm,*jlArm,*jlHand,*jrHand;

	char path[256] = {0};
	char *mdl = "data\\models\\chimi";
	sprintf(path,"%s\\legs.b3d",mdl);
	legs = smgr->addAnimatedMeshSceneNode(smgr->getMesh(path));
	sprintf(path,"%s\\torso.b3d",mdl);
	torso = smgr->addAnimatedMeshSceneNode(smgr->getMesh(path));

	sprintf(path,"%s\\head.b3d",mdl);
	head = smgr->addAnimatedMeshSceneNode(smgr->getMesh(path));

	sprintf(path,"%s\\larm.b3d",mdl);
	larm = smgr->addAnimatedMeshSceneNode(smgr->getMesh(path));

	sprintf(path,"%s\\rarm.b3d",mdl);
	rarm = smgr->addAnimatedMeshSceneNode(smgr->getMesh(path));

	sprintf(path,"%s\\lhand.b3d",mdl);
	lhand = smgr->addAnimatedMeshSceneNode(smgr->getMesh(path));

	sprintf(path,"%s\\rhand.b3d",mdl);
	rhand = smgr->addAnimatedMeshSceneNode(smgr->getMesh(path));

	jTorso = legs->getJointNode("torso");
	jHead = torso->getJointNode("head");
	jrArm = torso->getJointNode("rarm");
	jlArm = torso->getJointNode("larm");
	jlHand = larm->getJointNode("lhand");
	jrHand = rarm->getJointNode("rhand");
	
	jTorso->addChild(torso);
	jHead->addChild(head);
	jlArm->addChild(larm);
	jrArm->addChild(rarm);
	jlHand->addChild(lhand);
	jrHand->addChild(rhand);

	larm->setVisible(false);
	rarm->setVisible(false);

	legs->setPosition(vector3df(20,0,20));
	cam->setTarget(vector3df(20,50,20));

	scene::ISceneNodeAnimator* anim = smgr->createRotationAnimator(

			core::vector3df(0,0.3f,0));

	legs->addAnimator(anim);

	while (device->run())
	{
		driver->beginScene(true, true, video::SColor(0,220,220,255));

		// render the scene
		smgr->drawAll();

		driver->endScene();

		// Draw fps counter
		int fps = driver->getFPS();
		if (lastFPS != fps)
		{
			wchar_t tmp[1024];
			swprintf(tmp, 1024, L"Model Viewer [fps:%d] [triangles:%d]", 
				fps, driver->getPrimitiveCountDrawn());
			device->setWindowCaption(tmp);
			lastFPS = fps;
		}
	}

	device->drop();
	return 0;
}
dlangdev
Posts: 1324
Joined: Tue Aug 07, 2007 7:28 pm
Location: Beaverton OR
Contact:

Post by dlangdev »

#1) Check polygon count of each model. They should be at a reasonable count. Each of these meshbuffers will pass through the transform matrix for every render frame.

#2) Another thing to check is buffer memory layout, these vertices/normals/texcoords should be arranged nicely in memory, otherwise a lag factor could be added in there as well. Note that you have no control on how these buffers are implemented. I'm just saying you need to be aware of them. If it is too abstracted, it may contribute to lag.

#3) Keep in mind how #1 and #2 are somewhat related. When buffer memory is scattered, walking through them during transform time will take more time.

Start debugging on this line, see how many vectors are passing through the matrix transform. Run it through a profiler and see t1, t2, t3 and so on.

Code: Select all

legs->addAnimator(anim); 
...
smgr->drawAll(); 
Hehe, I know this is crazy, but that is how I'm going to do it, though.
Image
Post Reply