Rotate objects to normal?

I’m trying to rotate my object to match the normal of the ground. I can get the normal with a ray from a physx node but I do not know how to convert that into rotation for character or decal. The effect I am trying to achieve would be like bullet holes on a wall or making a Mario Galaxy Style game where I reorientate around an object like a sphere. Any guidance would be appreciated.

Hi @phil_blackwood,

I think the best way to do this is to create a new orthonormal basis for the vector and then use that to apply the rotation to your object.

There’s a pretty neat way to do this using an algorithm by John F. Hughes and Tomas Möller. It’s in the Real Time Rendering book (3rd edition, 4.24), we use a version of it in the White Box code in one of the util files you might be able to find too.

This paper could also be useful - https://www.google.com/url?sa=t&source=web&rct=j&url=http://cs.brown.edu/research/pubs/pdfs/1999/Moller-1999-EBA.pdf&ved=2ahUKEwik1eiJx-7rAhVxTxUIHfHgD0EQFjAJegQICBAB&usg=AOvVaw3S0kJSjnIWZrzIT_PmpDz9

2 Likes

Hello phil_blackwood,

to rotate an object so that it follows the terrain slope is totally easy, at least the basic function.

You could do it with a lookat rotation. You get the forward vector of your object, Then forward cross normal (from hit) you get the right vector. Then cross normal with the up vector, to get forward. Dont forget to normalize your vectors. Then use Transform::CreateFromColumns(right,forward,normal,position) and this is your new transform.

I don’t know if it is possible in Lumberyard to get the Triangle hit or the u and v vectors of the triangle hit. But if you get these, you could build your Transform or Geometry easily.

Joerg

@masm32
So I’m new to the matrices Vector math. Based on what you said this is what I came up with, with scrip canvas nodes. I’m also pretty newest script canvas nodes so I’m not sure if I’m using things properly. Any input you could provide to help me fix this code would be appreciated. it does not seem to do anything.

After thinking about it I realized my solution won’t work exactly how you’d want. I did a little digging and stumbled across these posts which are great and might also come in handy

Hello phil_blackwood,

I can say that your solution will not work for several reasons.

First doing it on the OnHeld event will only execute as long as this event gets fired.
Then you do a RayCast on Local Space. As far as I know you should take RayCastWorldSpace. If local space means the Entity local space (my understanding), then you have to transform all other Entities in your Local Space. If you do it in World Space, all Entities should be in the right Space.

You create a Transform and convert the Transform to a Euler Vector. This Vector values are angles, so you can’t plug this into World Gravity and Position.

I assume you want to do some sort of movement animation. You can’t do it this way. Do it on the OnHeld Event will only execute as long you held the button or whatever. You should set some sort of flag and then handle the jumping in an OnTick handler, so you have the Frame Delta Value as well. This Delta is the frame time from your rendering (and other computations) and you have to use it on animation and movement to get a similiar speed on different systems with different computation speed.

The LookAt Transform is useful if you have to align a car to the slope of a hill. You need two Vectors for it, the Forwars vector and the Up Vector as example. I use the Forward of my Entity and the hit normal to create a transform to rotate a car on the slope. This works for basic testing, but it is not flawless.

Here I made the RotateAlign from the links Tom provided. But it is not tested and I saved many values, which was not necessary.

And this is my prototyping for my Horse Movement. I use ScriptCanvas only for prototyping, so expect nothing really useful.

Joerg

1 Like