Search Unity

Some rotation questions

Discussion in 'Scripting' started by unitynoob24, May 20, 2015.

  1. unitynoob24

    unitynoob24

    Joined:
    Dec 27, 2014
    Posts:
    398
    Hey guys!

    I am doing some neat things with rotation and was having some issues.

    So I will keep this as simple as possible, when the player presses and holds a button (using Input.GetKey) the main camera rotates 90 degrees to the left. If the player releases the button, I use (Input.GetKeyUp) to rotate the camera back to where it belongs. This works great! However, yep you guessed it! When the player doesn't press the 'rotate' key long enough, then they release the key, the (Input.GetKeyUp) code launches, effectively moving the camera -90 degrees, from not a 90 degree location, and as you may have guess, that throws off everything.

    I think I need to track how far the camera moves (X) in my Input.GetKey then in my Input.GetKeyUp, just rotate in the opposite direction for (X).

    I have written all of it in JS.

    This is my Input.GetKey stuff:

    Code (csharp):
    1.  
    2. RotateObject(transform.rotation, Quaternion.Euler(transform.rotation.eulerAngles + Vector3.up * -90), 0.8);
    3.  
    This is the RotateObject function
    Code (csharp):
    1.  
    2.  
    3. function RotateObject(startRot: Quaternion, endRot : Quaternion, rotateTime : float){
    4.  
    5. var i = 0.0;
    6. var rate = 1.0/rotateTime;
    7.  
    8. while(i < 1.0)
    9. {
    10. i += Time.deltaTime * rate;
    11. transform.rotation = Quaternion.Lerp(startRot, endRot, Mathf.SmoothStep(0.0, 1.0, i));
    12. yield;
    13. }
    14.  
    15. }
    16.  

    Finally, this is the Input.GetKeyUp stuff:
    Code (csharp):
    1.  
    2. RotateObject(transform.rotation, Quaternion.Euler(transform.rotation.eulerAngles + Vector3.up * 90), 0.8);
    3.  
    I think I know what I have to do, like I mentioned above; track how far the camera spins, the on release spin in reverse.. I just do not have any idea how to do that. This is my first time using Quaternions and Eulers.

    Any help would be greatly appreciated!

    Thanks guys!
     
    Last edited: May 20, 2015
  2. LeftyRighty

    LeftyRighty

    Joined:
    Nov 2, 2012
    Posts:
    5,148
    [ code] [ /code] tags when you paste in code to the forums, formats better (there is a sticky for that at the top of the scripting subforum...)

    store the forward direction, then use Vector3.Angle(storedValue, currentForward) to get the angle by which the object is "off by" at the start of the keyup code, use that angle instead of 90 degrees
     
  3. unitynoob24

    unitynoob24

    Joined:
    Dec 27, 2014
    Posts:
    398
    Okay sorry about that!

    Thank you for the reply!

    Can you walk me through your suggestion? I'm not exactly sure how to work with and parse Vector3 infromation from objects.

    Thanks again
     
  4. LeftyRighty

    LeftyRighty

    Joined:
    Nov 2, 2012
    Posts:
    5,148
    something like this... (I'm not a 2d js programmer so might have typos from 3d c# syntax :D )

    declare the class variable
    Code (csharp):
    1.  
    2. originalFacing : Vector3; // or vector2 if it's a 2d project i think...
    3.  
    in "Input.GetKeyDown(...)" note the "down" we only want this to happen once when the key is first pressed, not be updated every frame the button is held down.
    Code (csharp):
    1.  
    2. originalFacing = transform.forward;
    3.  
    in "Input.GetKeyUp"
    Code (csharp):
    1.  
    2. float angle = Vector3.Angle(originalFacing, transform.forward);
    3. RotateObject(transform.rotation, Quaternion.Euler(transform.rotation.eulerAngles + Vector3.up * angle), 0.8);
    4.  
     
  5. unitynoob24

    unitynoob24

    Joined:
    Dec 27, 2014
    Posts:
    398
    Okay awesome! This sounds perfect!

    When I put all of this in, it is telling me (114,22) UCE0001: ';' expected. Insert semicolon at the end.

    That is line #2 in the Input.GetKeyUp.. I have a semi colon, everything looks fine, I did it just how you have done it here. Is there possibly something else wrong with the angle related syntax?

    EDIT
    I figured it out! I am using JS so I just took out the float and put in var and it worked great!

    Seems like it still needs some tweaking, but I am now accessing the values that I was trying to get!

    Thanks again! It has been very appreciated
     
    Last edited: May 20, 2015
  6. LeftyRighty

    LeftyRighty

    Joined:
    Nov 2, 2012
    Posts:
    5,148
    oh, yeah, js should be

    Code (csharp):
    1.  
    2. var angle : float = ...
    3.  
    *points at disclaimer in line 1 lol* :cool:

    Glad to help :D
     
  7. unitynoob24

    unitynoob24

    Joined:
    Dec 27, 2014
    Posts:
    398
    I wanted to thank you again for helping me with my rotation issue. I seemed to have implemented what you helped me with about 90% but am getting strange issues with one of my rotations. In order to isolate the problem I am working on just the area in question in it's own file. What is happening is at the simplest form, when the player presses a button, using GetKeyDown I rotate the camera 180 degrees, then when they release I use the angle handling that you helped me with, and it works decent, but only if I hold the rotate button down long enough for the full 180 degree rotation. I would like it so, the player can tap the rotation button, they have to wait for the entire rotation to take place, then the rotation goes in reverse and they must wait until it swings back forward.

    Here is what I set up, sorry this is in JS.

    My Start function:

    Code (csharp):
    1.  
    2. originalFacing = transform.forward;
    3.  
    My Update:

    Code (csharp):
    1.  
    2. if(Input.GetKeyDown("q"))
    3. {
    4. RotateObject(transform.rotation, Quaternion.Euler(transform.rotation.eulerAngles + Vector3.up * 180), 1.0);
    5. }
    6.  
    7. if(Input.GetKeyUp("q"))
    8. {
    9. _angle = Vector3.Angle(originalFacing, transform.forward);
    10. RotateObject(transform.rotation, Quaternion.Euler(transform.rotation.eulerAngles + Vector3.up * _angle), 1.0);
    11. }
    12.  
    My Rotate function:

    Code (csharp):
    1.  
    2. function RotateObject(startRot: Quaternion, endRot : Quaternion, rotateTime : float)
    3. {
    4.  
    5.     var i = 0.0;
    6.     var rate = 1.0/rotateTime;
    7.  
    8.     while(i < 1.0)
    9.     {
    10.    
    11.     i += Time.deltaTime * rate;
    12.    
    13.     transform.rotation = Quaternion.Lerp(startRot, endRot, Mathf.SmoothStep(0.0, 1.0, i));
    14.    
    15.     yield;
    16.    
    17.     }
    18.  
    19. }
    20.  
    So what I am going for is, I would like it so if the player taps the rotate button, they are forced to let it rotate 180 degrees, once the camera rotates 180 degrees and the player releases the rotate key I want it to rotate in reverse. What I have here works if the player holds the rotate key until the 180 degrees has been rotated, then it goes in reverse once they release the rotate key. The way it sits now, if the player releases the rotate key before the camera rotates 180 degrees, the camera finishes its 180 degree rotation, then it just blinks back to where it started but is always offset by an odd number of degrees, which I am assuming are the negative value of wherever the player releases the rotate key prematurely.

    Basically I want it so if the player hits rotate, it rotates all the way 180, then all the back 180. If they are holding the rotate key I would like it to rotate 180 degrees and stay rotated 180, until they release it, then I would like it to rotate back 180 degrees. I know this is possible and I have it working for other angles, I just can't seem to get it working for 180.

    Thanks in advance!
     
  8. unitynoob24

    unitynoob24

    Joined:
    Dec 27, 2014
    Posts:
    398