Unity3d: Rotate a gameobject towards forward vector of another gameobject - c#

BackCube.position = cameraEye.position - cameraEye.forward * 2;
float back = cameraEye.position.z - 2f;
BackCube.position = new Vector3(BackCube.position.x, BackCube.position.y, back);
var lookPosBack = cameraEye.position - BackCube.position;
lookPosBack.y = 0;
var rotationBack = Quaternion.LookRotation(lookPosBack);
BackCube.rotation = Quaternion.Slerp(BackCube.rotation, rotationBack, 1);
So, I want the my BackCube to rotate towards the forward vector of cameraEye. The code above looks at the cameraEye, but not towards the forward vector of cameraEye. I want the forward vectors of both pointing at each other being 2 units apart from each other. I have control only over the BackCube

This worked!
Vector3 direction = Vector3.ProjectOnPlane(cameraEye.forward, Vector3.up);
BackCube.transform.position = cameraEye.position - direction.normalized * 2;
var lookPosBack = cameraEye.position - BackCube.position;
lookPosBack.y = 0;
var rotationBack = Quaternion.LookRotation(lookPosBack);
BackCube.rotation = Quaternion.Slerp(BackCube.rotation, rotationBack, 1);

Related

Rotate empty object around center

I manually (from editor) create empty object with boxes. It rotate around center.
But if I create same object with boxes from script. It rotate around unknown point for me.
I found the cause. It happening because boxes has scale (0.1, 0.2, 0.1). If I set (1,1,1) - it work.
How to fix it? I want small boxes.
var wall = new GameObject();
//wall.transform.parent = room.transform;
wall.transform.name = "Wall";
wall.transform.position = new Vector3(0,0,0);
for (int x = -3; x < width-3; x++)
{
for (int y = -3; y < height-3; y++)
{
var plate = Instantiate(SimplePlate);
var pos = plate.transform.position;
float posZ = pos.z - (x * plate.transform.lossyScale.z);
float posY = pos.y + (y * plate.transform.lossyScale.y);
var newPos = new Vector3(0, posY, posZ);
plate.transform.position = newPos;
plate.transform.parent = wall.transform;
plate.name = "Plate " + x;
}
}
You could create another empty GameObject and stuff your box inside. Then rotate the parent you just created?
Also, how can you rotate an object with a scale of (0,0,0). Did you mean (1,1,1)?

Calculate position on ground for camera

I'm trying to calculate the position on the ground that a camera is looking at (without doing a raytrace since I know the forward vector of the camera and the height of the ground). I tried doing this using the dot product but I still seem to be getting the wrong answer. This is what I did with the values I was testing with:
const float groundHeight = 0f;
Vector3 cameraPosition = new Vector3(0f, 3f, 0f);
Vector3 cameraForward = new Vector3(0f, -0.7f, 0.7f); //Unit vector
Vector3 positionOnGround = cameraPosition;
positionOnGround.y = groundHeight;
Vector3 cameraToGround = positionOnGround - cameraPosition;
float scalar = Vector3.Dot(cameraToGround, cameraForward);
Vector3 forwardToGround = cameraForward * scalar;
return cameraPosition + forwardToGround;
For some reason this is giving me the position 0, 1.5, 1.5 when I'm looking for something that has a height of 0. Any ideas of what I'm doing wrong?
Let's define:
camera is located at point C.
camera is looking at its target point on the ground (P) (you want to find P)
camera distance from ground yC = camera.transform.position.y
camera projection on the ground (G)
distance of p from G (zP)
angle of GCP is a. which in your case it's 45 degrees since CP is (0f, -0.7f, 0.7f)
Now
tan(a) = magnitude(PG) / magnitude(CG)
= zP / yC
= zP / camera.transform.position.y
P = new Vector3(xP,yP,zP)
= new Vector3(xC,0,zP)
= new Vector3(camera.transform.position.x, 0, tan(a)*camera.transform.position.y)

Align 3d Object to Camera position

I am using the Viewport control to visualize 3d Tool Models with the help of AB4D PowerToys.
Currently I'm trying to align my 3D Text (which is a group of lines) to the camera, so it rotates always to the camera and appears like 2D text.
Is it possible to bind the Transformation of my Visual to the position of my camera?
Finally found the answer myself:
The following code should be called on the "CameraChanged" Event.
private void UpdateTransforms()
{
if (!this.IsAttachedToViewport3D())
{
return;
}
Matrix3D view, projection;
if (Camera.GetCameraMatrixes(out view, out projection))
{
Vector3D up = new Vector3D(view.M12, view.M22, view.M32);
Vector3D look = new Vector3D(view.M13, view.M23, view.M33);
Transform3D transform = Transform;
Matrix3D inverseWorld = this.GetTransform();
inverseWorld.Invert();
look = inverseWorld.Transform(look);
look.Normalize();
up = inverseWorld.Transform(up);
up.Normalize();
Quaternion q = LookAtRotation(look, up);
Transform3DGroup grp = new Transform3DGroup();
grp.Children.Add(new RotateTransform3D(new QuaternionRotation3D(q), CenterPosition));
grp.Children.Add(transform);
Transform = grp;
Camera.Refresh();
}
}
private static Quaternion LookAtRotation(Vector3D lookAt, Vector3D upDirection)
{
Vector3D forward = lookAt;
Vector3D up = upDirection;
// Orthonormalize
forward.Normalize();
up -= forward * Vector3D.DotProduct(up, forward);
up.Normalize();
Vector3D right = Vector3D.CrossProduct(up, forward);
Quaternion q = new Quaternion
{
W = Math.Sqrt(1.0 + right.X + up.Y + forward.Z) * 0.5
};
double w4Recip = 1.0 / (4.0 * q.W);
q.X = (up.Z - forward.Y) * w4Recip;
q.Y = (forward.X - right.Z) * w4Recip;
q.Z = (right.Y - up.X) * w4Recip;
return q;
}

Planet rotate around its local y-axis using Matrix4x4

I am having a bit of trouble figuring out how to rotate a sphere (planet) from a starting static position around it's local y-axis using a Matrix4x4 with custom rotation formulas. The planet doesn't rotate at all. I've posted the code below. Thanks for any advice.
Note: ori would be the degrees per second it would rotate
void OrientationRate()
{
Matrix4x4 o = new Matrix4x4();
float theta = ori * Time.fixedDeltaTime;
o[0, 0] = Mathf.Cos(theta);
o[0, 2] = -Mathf.Sin(theta);
o[2, 0] = Mathf.Sin(theta);
o[2, 2] = Mathf.Cos(theta);
Vector4 p = this.transform.eulerAngles;
p.w = 1;
Vector4 pprime = (o * p);
//set the new position
this.transform.Rotate(new Vector3(pprime.z, pprime.x, pprime.y) * Time.fixedDeltaTime);
}

XNA Rotating multiple objects around a pivot point

Here is my code. It works, except for when I do it at first It jumps far away from where it started, and as it's rotating its twitching and sort of flipping rapidly...
float rotAmount = 0;
Vector2 pivot = CenterSelection();
if (keyboardState.IsKeyDown(Keys.OemPlus)) rotAmount = 0.01f;
if (keyboardState.IsKeyDown(Keys.OemMinus)) rotAmount = -0.01f;
map.DoForSelected(delegate(GameObject mod)
{
Vector2 vDif = pivot - mod.position;
float vDist = (float)Math.Sqrt(Math.Pow(vDif.X, 2) + Math.Pow(vDif.Y, 2));
float vRot = rotAmount + (float)Math.Atan2(vDif.Y, vDif.X);
mod.position = pivot + new Vector2(
(float)Math.Cos(vRot),
(float)Math.Sin(vRot)
) * vDist;
mod.rotation += rotAmount;
});
I am trying to figure out what's wrong!
Your help is greatly appreciated!
Your difference vector points in the wrong direction:
Vector2 vDif = pivot - mod.position;
This is a vector from position to pivot.
Then you assign
mod.position = pivot + newDif;
expecting that newDif is a vector from pivot to position. But it's actually reversed.
So just reverse your difference vector:
Vector2 vDif = mod.position - pivot;

Categories

Resources