The Matrix

If you are a new Irrlicht Engine user, and have a newbie-question, this is the forum for you. You may also post general programming questions here.
Post Reply
Oz
Posts: 81
Joined: Tue Aug 31, 2004 3:34 pm

The Matrix

Post by Oz »

No, not the film but I am trying to get noobies attention anyway! ;)

After helping someone get the inward vector from a matrix ive realised it is ordered different to some other ones. So, hes the code for getting the Left (fixed), Up and In vectors from a matrix.
/*
0 1 2 3 // right(0,1,2) (-right for left)
4 5 6 7 // up(4,5,6)
8 9 10 11 // in(8,9,10)
12 13 14 15
*/
NOTE: Im using a camera as an example, any scenenode should do:
In:

Code: Select all

	matrix4 cameramatrix = camera->getRelativeTransformation();

	vector3df	in(	cameramatrix.M[8],
					cameramatrix.M[9],
					cameramatrix.M[10]);
	vector3df pos = camera->getPosition();

	pos += in;
	camera->setPosition(pos);
Up:

Code: Select all

	matrix4 cameramatrix = camera->getRelativeTransformation();
	vector3df	up(	cameramatrix.M[4],
					cameramatrix.M[5],
					cameramatrix.M[6]);

	vector3df pos = camera->getPosition();
	pos += up;
	camera->setPosition(pos);
Left: (loose the - for right)

Code: Select all

	matrix4 cameramatrix = camera->getRelativeTransformation();

	vector3df	left(	-cameramatrix.M[0],
					-cameramatrix.M[1],
					-cameramatrix.M[2]);
	vector3df pos = camera->getPosition();

	pos += left;
	camera->setPosition(pos);
Hope this helps!

EDIT: Oh yeah, -Up is Down, -In is Back (duh!)
pos+=in*scale;
Is how you alter the speed. (its 1 unit normally)
So:
pos+=in*5;
makes your camera (or whatever scenenode) whiz forward fast!

See: (where this madness began) :D
http://irrlicht.sourceforge.net/phpBB2/ ... php?t=3705
Last edited by Oz on Mon Sep 06, 2004 4:32 pm, edited 1 time in total.
"When we looked at the relics of the precursors, we saw what heights civilization can attain.
When we looked at their ruins, we marked the danger of that height." -Keeper Annals
(Thief2: The Metal Age)
Guest

Post by Guest »

After thinking about it, im going to be so bold as to say these should be functions built into the matrix4 class.
What do you think?

vect3df matrix4::getLeft()
vect3df matrix4::getUp()
vect3df matrix4::getIn()
And
matrix4 matrix4::setFromLeftUpIn()

?
Oz
Posts: 81
Joined: Tue Aug 31, 2004 3:34 pm

Post by Oz »

Oops that was me.
Im pretty new to C++ so my implementation idea prolly sucks.
I know id make use of these (top 3) member functions ALOT though.
The 4th is a little dangerous. You have to assert that its orthonormal, or is it orthogonal. (I drink too much, but I hate mondays)
"When we looked at the relics of the precursors, we saw what heights civilization can attain.
When we looked at their ruins, we marked the danger of that height." -Keeper Annals
(Thief2: The Metal Age)
Oz
Posts: 81
Joined: Tue Aug 31, 2004 3:34 pm

Post by Oz »

OK I think this could be a little hard to understand for some so I re-wrote the EventReciever from Tutorial 4:Movement.
Just paste this in its place (comment out the old event reciever)

Code: Select all

class MyEventReceiver : public IEventReceiver
{
public:
	virtual bool OnEvent(SEvent event)
	{
		/* IrrLicht matrix4
		0  1  2  3	//	right(0,1,2) (-right for left)
		4  5  6  7	//	up(4,5,6)
		8  9  10 11	//	in(8,9,10)
		12 13 14 15
		*/

		if (node != 0 && event.EventType == irr::EET_KEY_INPUT_EVENT&&
			!event.KeyInput.PressedDown)
		{
			core::matrix4		matrix = node->getRelativeTransformation();
			core::vector3df		pos = node->getPosition();

			switch(event.KeyInput.Key)
			{
			case KEY_KEY_A:	//	left
				{
					core::vector3df	left(	-matrix.M[0],
											-matrix.M[1],
											-matrix.M[2]);
					
					pos += left;
					node->setPosition(pos);
				}
				return true;
			case KEY_KEY_W:	//	up
				{
					core::vector3df	up(	matrix.M[4],
										matrix.M[5],
										matrix.M[6]);
					
					pos += up;
					node->setPosition(pos);
				}
				return true;
			case KEY_KEY_S:	//	in
				{
					core::vector3df	in(	matrix.M[8],
										matrix.M[9],
										matrix.M[10]);
					
					pos += in;
					node->setPosition(pos);
				}
				return true;
			}
		}

		return false;
	}
};
Keys (ASW)
Handy huh? Why faff with sin & cos all the time? Works for me!
"When we looked at the relics of the precursors, we saw what heights civilization can attain.
When we looked at their ruins, we marked the danger of that height." -Keeper Annals
(Thief2: The Metal Age)
Oz
Posts: 81
Joined: Tue Aug 31, 2004 3:34 pm

Post by Oz »

Hehe, looks like ive touched an OpenGL vs DirectX & Lefthanded vs Righthanded nerve

Well its up to you. I know ill keep using this in OpenGL & DirectX, you can too.
(Now im gonna run before im beaten up)

-Ozzy
"When we looked at the relics of the precursors, we saw what heights civilization can attain.
When we looked at their ruins, we marked the danger of that height." -Keeper Annals
(Thief2: The Metal Age)
Oz - AWOL

Post by Oz - AWOL »

:cry:
Im leavining cuz ive maybe said too much.

Bye and good luck, Ozzy.
Oz
Posts: 81
Joined: Tue Aug 31, 2004 3:34 pm

Post by Oz »

No screw it. Im not leaving. :evil:

I like this community and I think most like me too.
Ill post 10 times in a row if I think im helping people. This is Niko's forum. If he tells me to leave I will, right away.
If you dont like my matrix4 mod or if you think its wrong or it sucks, then dont use it.

Im not trying to prove im smarter than anyone afterall. These are really usefull functions that I cant believe you lived without!
"When we looked at the relics of the precursors, we saw what heights civilization can attain.
When we looked at their ruins, we marked the danger of that height." -Keeper Annals
(Thief2: The Metal Age)
Robomaniac
Posts: 602
Joined: Sat Aug 23, 2003 2:03 am
Location: Pottstown, PA
Contact:

Post by Robomaniac »

Who said anything bad about you mod? Was there any provoked reason you got so angry?
The Robomaniac
Project Head / Lead Programmer
Centaur Force
Oz
Posts: 81
Joined: Tue Aug 31, 2004 3:34 pm

Post by Oz »

I was just being a baby. Dont worry about it.
"When we looked at the relics of the precursors, we saw what heights civilization can attain.
When we looked at their ruins, we marked the danger of that height." -Keeper Annals
(Thief2: The Metal Age)
zola
Posts: 52
Joined: Thu Jul 15, 2004 2:31 pm
Location: switzerland
Contact:

Post by zola »

Cool Oz this really helps me a lot :)

It would be nice if Your tip would be part of the engines matrix class.
To summarize it (please correct me if I'm wrong)

Code: Select all

//get the local axis defined by the matrix
void getAxis(vector3df& xA, vector3df& yA, vector3df& zA);

vector3df getXAxis();

vector3df getYAxis();

vector3df getZAxis();


// and the implementation
void matrix4::getAxis(vector3df& xA, vector3df& yA, vector3df& zA)
{
 xA.set(m[0],m[1],m[2]);
 yA.set(m[4],m[5],m[6]);
 zA.set(m[8],m[9],m[10]);
}

vector3df matrix4::getXAxis()
{
 return vector3df(m[0],m[1],m[2]);
}

vector3df matrix4::getYAxis()
{
 return vector3df(m[4],m[5],m[6]);
}

vector3df matrix4::getZAxis()
{
 return vector3df(m[8],m[9],m[10]);
}

Since irrlicht handles matrix transformation from irrlicht matrix format to D3D and OGL itself this will be correct for every driver type.

Now, I don't know what happens if the matrix has also a scaling component, or if scaling is an issue at all? (I think I have to polish up my math ;) )

Anyway, thanks for the code

Cheers
Z
Oz
Posts: 81
Joined: Tue Aug 31, 2004 3:34 pm

Post by Oz »

@zola
Thank you. I was beggining to feel like wasted-space. :(

Your implementation seems to be right to me. (Different but not erranous I think)

Im wishing I never brought this up BUT on the bright side, I helped the guy who originally posted his problem. :) Hurray!

Score 1 for Ozzy! lol

EDIT: I got mad because I got into a fight about this with some of my friends. I kicked their asses so dont worry. :)

Alright ive to to rant about why I got in such a foul mood. I has helping a friend (a real life friend) who uses IrrLicht and I was trying to explain to him how you could use these little functions to make cool effects. I figured, ill just zip up the project and send it to him via email. BIG mistake I forgot to clean the project so the executable was in there. He saw it and accused me of trying to hack him. We got into a massive argument as he was scanning it (which was harmless, obviously) with like a dozen virus scanners in the end he was getting in touch with my ISP. I just went ballistic! :(
I think he even sent it to mcafee. LOL how embarassing. I hope they tell him hes a dork.
(Were kind of not arguing anymore)
<rant over>

EDIT: PS Sorry for being a bit of an a$$hole but he reads these forums too.
"When we looked at the relics of the precursors, we saw what heights civilization can attain.
When we looked at their ruins, we marked the danger of that height." -Keeper Annals
(Thief2: The Metal Age)
Yan

Post by Yan »

Oz, which ones in the matrix are the translation? Im thinking of making a function to build the matrix from those vectors and the translation too.

Thanks.

Oh and if I had friends like yours id leap from a cliff! j/k
Yan

Post by Yan »

Oops sorry. it was pretty obvious

inline vector3df matrix4::getTranslation() const
{
return vector3df(M[12], M[13], M[14]);
}

Thanks
Seven
Posts: 1030
Joined: Mon Nov 14, 2005 2:03 pm

Post by Seven »

sorry to be so dense about this, but i cannot seem to get this working correctly. the camera does not react as I need it to, but seems to rotate as it moves. as long as i only move in and out, then the camera looks fine, but as soon as i move left or right, then the camera seems like it is still looking 'at' something and rotates instead of strafes. all i am really trying to do is have the camera move forward, reverse, and strafe left and right. anyhow, it is an MFC app and i have the camera movement setup like this.. any help would be appreciated

Code: Select all

	// TODO: Add your message handler code here and/or call default
	CZEditDoc* pDoc = GetDocument();
	ASSERT_VALID(pDoc);

	if (pDoc) 
	{	
		// get the 'in' of the camera
		matrix4 cameramatrix = pDoc->m_Cam->getRelativeTransformation(); 
		core::vector3df in(cameramatrix.M[8],cameramatrix.M[9],cameramatrix.M[10]); 
		in.normalize();

		core::vector3df left(-cameramatrix.M[0],-cameramatrix.M[1],-cameramatrix.M[2]); 
		left.normalize();

		// get the current camera position
		core::vector3df vec = pDoc->m_Cam->getPosition();

		switch (nChar)
		{
			case VK_UP		: vec += in*pDoc->m_Speed; break;
			case VK_DOWN	: vec -= in*pDoc->m_Speed; break;
			case VK_LEFT	: vec += left*pDoc->m_Speed; break;
			case VK_RIGHT	: vec -= left*pDoc->m_Speed; break;
		}

		pDoc->m_Cam->setPosition(vec);
	}

Post Reply