- Home /
lower and upper body rotation
Hello. Being fairly new to the world of coding, I am facing a problem.
I have the typical behavior of a human body to apply.
I have the upper body is a child of the lower body. it is on the lower body that my script is attached.
The upper body must turn to + 45 ° - 45 ° (min... an max.... var). If one tries to turn over, the entire body rotating at 45 ° (and so on). For the upper body (upperCube), I did this:
var sensitivity : float = 5; var xRotation : float; var lowerCubeRotation : float; var upperCube : GameObject; var minUpperCubeXRotation = -45; var maxUpperCubeXRotation = 45;
function Update () { var controller = GetComponent(CharacterController); xRotation += Input.GetAxis("Mouse X") * sensitivity; Rotation(); }
function Rotation() { if (xRotation > maxUpperCubeXRotation){ }
if (xRotation < minUpperCubeXRotation){ }
upperCube.transform.localEulerAngles = Vector3(0, xRotation, 0);
} So the upper body rotates and if it reaches one of the limits, the lower body must perform a rotation of 45 ° (var lowerCubeRotation) over a period of 3 seconds (to be defined in a var) and the upper body returns to allignment with the lower body.
But how to code the part of the lower body. As I said, I suck. I tested:
transform.Rotate(0, lowerCubeRotation, 0);
xRotation -= minUpperBodyXRotation;
which applies a rotation of 45 ° to transform (lower body), but instantly. And a rotation of the upper body to 0 (at the bottom allignment).
My problem lies in the duration of the rotation. I want it to end after x seconds, not immediately.
need help please. (post on unity forum)
use google translate
Answer by aldonaletto · Jan 30, 2012 at 12:03 AM
You're in the right path: use euler angles to set the rotation, and always set x, y and z at the same time. You can use Mathf.MoveTowards to move only the angle y at constant speed (degrees per second): save the initial lower part euler angles, and when the upper part goes out of the limits, add the upper rotation to the initial lower part y angle, then set the new target angle.
var sensitivity : float = 5; var xRotation : float; var lowerCubeRotation : float; var upperCube : GameObject; var minUpperCubeXRotation = -45; var maxUpperCubeXRotation = 45; var speed: float = 180; // degrees per second
private var targetAngle: float; // angle around y to reach private var curAngle: float; // current angle around y private var iniAngle: Vector3; // initial complete euler angles private var controller: CharacterController;
function Start(){ controller = GetComponent(CharacterController); iniAngle = transform.eulerAngles; // save the complete initial euler angles targetAngle = iniAngle.y; // initialize the target... curAngle = iniAngle.y; // and the current Y angles }
function Update () { xRotation += Input.GetAxis("Mouse X") * sensitivity; Rotation(); }
function Rotation() { // set the upper part rotation (use modulo 360 to avoid crazy rotations): upperCube.transform.localEulerAngles = Vector3(0, xRotation % 360, 0); if (xRotation > maxUpperCubeXRotation || xRotation < minUpperCubeXRotation){ // if xRotation gone out of limits... targetAngle = iniAngle.y + xRotation; // find the new target angle } // "move" the current angle gradually each update... curAngle = Mathf.MoveTowards(curAngle, targetAngle, speed * Time.deltaTime); // keep the original x and z angles, and set the current angle modulo 360 transform.eulerAngles = Vector3(iniAngle.x, curAngle % 360, iniAngle.z); }
Answer by yoyoyaya · Jan 30, 2012 at 10:00 PM
Thank you for the answer. I used some of what you said for this:
var sensitivity : float = 5; var xRotation : float; var upperBodyXRotation : float; var speed: float = 180; var upperBody : GameObject; var minUpperBodyXRotation : float; var maxUpperBodyXRotation : float;
private var transformTargetAngle : float; private var transformCurrentAngle : float; private var transformInitialAngle : Vector3;
function Start() { controller = GetComponent(CharacterController); transformInitialAngle = transform.eulerAngles; transformTargetAngle = transformInitialAngle.y; transformCurrentAngle = transformInitialAngle.y; }
function Update () { xRotation += Input.GetAxis("Mouse X") * sensitivity; upperBodyXRotation = xRotation; if (upperBodyXRotation > maxUpperBodyXRotation) { upperBodyXRotation = maxUpperBodyXRotation; } if (transform.eulerAngles.y == transformTargetAngle) { transformInitialAngle = transform.eulerAngles; } Rotation(); }
function Rotation() { if (upperBodyXRotation == maxUpperBodyXRotation) { upperBodyXRotation -= maxUpperBodyXRotation; transformTargetAngle = transformInitialAngle.y + maxUpperBodyXRotation; transformCurrentAngle = Mathf.MoveTowards(transformCurrentAngle, transformTargetAngle, speed * Time.deltaTime); transform.eulerAngles = Vector3(transformInitialAngle.x, transformCurrentAngle % 360, transformInitialAngle.z);
}
upperBody.transform.eulerAngles = Vector3(0, xRotation % 360, 0);
}
in this case, when the upper body reaches 45 ° (maxUpperBodyXRotation), it runs the function that turns the lower body 45 degrees. The upper body is found at 0 ° with:
upperBodyXRotation -= maxUpperBodyXRotation;
logically, when I start again to turn the upper body 45 °, rotation of the lower basin should turn 45 degrees but it does not. "upperBodyXRotation" reste à 0.
I think for the rotation of the lower body, just change the "transform.eulerAngles" of "transformInitialAngle = transform.eulerAngles" by the new "transform.eulerAngles" from rotation function.
I tested this to reassign "transform.eulerAngles" with that obtained in the rotation function but it does not work:
if (transform.eulerAngles.y == transformTargetAngle) { transformInitialAngle = transform.eulerAngles; }
So to summarize, at present, I can rotate that lasts x seconds at the bottom of the body when the upper body is "maxUpperBodyXRotation" but this only works once. How can it be repeated?
I want that if the upper body rotates at an angle of 45 ° (maxUpperBodyXRotation) from the lower body, lower body rotates 45 ° ("maxUpperBodyXRotation" or other). Thus, the upper body is at the same rotation as the lower body (0, allignment upper and lower body) and subsequently, the action can be repeated.
May I ask a lot. But from the world of 3D, I know very little the world of the script. I learn every day a little more but sometimes I stuck. So if someone can give me his help, thank you.