Wayback Machinekoobas.hobune.stream
May JUN Jul
Previous capture 13 Next capture
2021 2022 2023
1 capture
13 Jun 22 - 13 Jun 22
sparklines
Close Help
  • Products
  • Solutions
  • Made with Unity
  • Learning
  • Support & Services
  • Community
  • Asset Store
  • Get Unity

UNITY ACCOUNT

You need a Unity Account to shop in the Online and Asset Stores, participate in the Unity Community and manage your license portfolio. Login Create account
  • Blog
  • Forums
  • Answers
  • Evangelists
  • User Groups
  • Beta Program
  • Advisory Panel

Navigation

  • Home
  • Products
  • Solutions
  • Made with Unity
  • Learning
  • Support & Services
  • Community
    • Blog
    • Forums
    • Answers
    • Evangelists
    • User Groups
    • Beta Program
    • Advisory Panel

Unity account

You need a Unity Account to shop in the Online and Asset Stores, participate in the Unity Community and manage your license portfolio. Login Create account

Language

  • Chinese
  • Spanish
  • Japanese
  • Korean
  • Portuguese
  • Ask a question
  • Spaces
    • Default
    • Help Room
    • META
    • Moderators
    • Topics
    • Questions
    • Users
    • Badges
  • Home /
avatar image
0
Question by azmundai · Jun 05, 2013 at 12:00 AM · rotationquaternioneulerrollpitch

Rotate on 2 different axes

I am trying to create a ship controller that will rotate the ship for roll and pitch. It's a hard concept for me as I don't fully understand what yaw is either. But that is besides the point, I think.

The issue I am having is that if I rotate around the z axis, I can limit rotation to 30 degrees, creating roll. I can then rotate around x axis and limit the rotation to 15.

Both work fine. I think I was pulling the local angles to check for the limit.

The problem is when I rotate around both, the object begins to tumble.

Sorry I have scrapped the old code so all I have left is this explanation. I've tried a ton of different approaches but cannot seem to solve this.

Can anyone point me in the right direction? Links or functions to use? An explanation of how to limit the amount of pitch and roll? I don't really want code .. I want to be able to understand this kind of stuff so I can apply it to future controllers.

Thanks :) azmundai

Comment
Add comment · Show 2
10 |3000 characters needed characters left characters exceeded
▼
  • Viewable by all users
  • Viewable by moderators
  • Viewable by moderators and the original poster
  • Advanced visibility
Viewable by all users
avatar image robertbu · Jun 05, 2013 at 12:26 AM 0
Share

You might be interested:

http://keithmaggio.wordpress.com/2011/07/01/unity-3d-code-snippet-flight-script/

One trick to limits is to treat any changes in eulerAngles as write-only and use your own Vector3 for making changes.

avatar image azmundai · Jun 05, 2013 at 04:38 AM 0
Share

Ok here is what I have .. it works pretty well, but the angles still slide too far when I pitch and roll at the same time.

 using UnityEngine;
 using System.Collections;
 
 public class GliderController : $$anonymous$$onoBehaviour {
     public float moveSpeed = 0.1f;
     private int maxSpeed = 32;
     public int turnSpeed = 6;
     public float rollSpeed = 0.1f;
     public float pitchSpeed = 0.2f;
     
     public float roll;
     public float pitch;
     
     public float rollAngle;
     public float pitchAngle;
     private float max$$anonymous$$ch = 15.0f;
     private float maxRoll = 35.0f;
             
     private Vector3 moveDirection = Vector3.zero;
     public CharacterController controller;
     private Transform player$$anonymous$$odel;
 
     // Use this for initialization
     void Start () {
         controller = GetComponent<CharacterController>();
         player$$anonymous$$odel = transform.FindChild("Player$$anonymous$$odel");
     }    
     
     // Update is called once per frame
     void Update () {
         Quaternion addRot = Quaternion.identity;
         
         if(moveSpeed < maxSpeed)
             moveSpeed += moveSpeed * Time.deltaTime;
                                     
         if(moveSpeed > maxSpeed) 
             moveSpeed = maxSpeed;
         
         moveDirection = new Vector3( 0, 0, moveSpeed );
         
         roll = pitch = 0;
         if( (rollAngle + (Input.GetAxis("Horizontal") * rollSpeed * Time.deltaTime) < maxRoll) && Input.GetAxis("Horizontal") > 0){
                 roll = Input.GetAxis("Horizontal") * rollSpeed * Time.deltaTime;
                 rollAngle += Input.GetAxis("Horizontal") * rollSpeed * Time.deltaTime;
         }
         if( (rollAngle + (Input.GetAxis("Horizontal") * rollSpeed * Time.deltaTime) > -maxRoll) && Input.GetAxis("Horizontal") < 0){
                 roll = Input.GetAxis("Horizontal") * rollSpeed * Time.deltaTime;
                 rollAngle += Input.GetAxis("Horizontal") * rollSpeed * Time.deltaTime;
         }
         if( (pitchAngle + (Input.GetAxis("Vertical") * pitchSpeed * Time.deltaTime) < max$$anonymous$$ch) && Input.GetAxis("Vertical") > 0){
                 pitch = Input.GetAxis("Vertical") * pitchSpeed * Time.deltaTime;
                 pitchAngle += Input.GetAxis("Vertical") * pitchSpeed * Time.deltaTime;
         }
         if( (pitchAngle + (Input.GetAxis("Vertical") * pitchSpeed * Time.deltaTime) > -max$$anonymous$$ch) && Input.GetAxis("Vertical") < 0){
                 pitch = Input.GetAxis("Vertical") * pitchSpeed * Time.deltaTime;
                 pitchAngle += Input.GetAxis("Vertical") * pitchSpeed * Time.deltaTime;
         }
         
         addRot.eulerAngles = new Vector3(-pitch, 0, -roll);
         
         player$$anonymous$$odel.localRotation *= addRot;        
         
         //transform direction
         moveDirection = transform.TransformDirection(moveDirection);
         
         transform.Rotate(0 , Input.GetAxis("Horizontal") * turnSpeed * Time.deltaTime, 0, 0);
         
         controller.$$anonymous$$ove(moveDirection * Time.deltaTime);
     }
 }

1 Reply

· Add your reply
  • Sort: 
avatar image
0

Answer by azmundai · Jun 05, 2013 at 07:47 AM

Ok I think I have this working. I actually switched to rotatearound ... again (i had tried it before but it had a similar problem) ... it was still not resetting the rotation right until I added the slerps. Any other suggestions welcome :)

EDIT 1 : took out some bools I didn't need, added comments.

 using UnityEngine;
 using System.Collections;
 
 public class GliderControllerTwo : MonoBehaviour {
     public float moveSpeed = 1.0f;                    // Speed at which glider is moving
     private int maxSpeed = 64;                        // Maximum Speed of glider (when pitching forward).
     public int glideSpeed = 32;                        // Gliding Speed (neutral stick)
     public int turnSpeed = 50;                        // Speed glider turns; rotates
     public float rollSpeed = 2.0f;                    // Speed at which model rotates when rolling.
     public float pitchSpeed = 1.2f;                    // Speed at which model rotates when pitching.
     public float altitudeChangeSpeed;                // Speed at which model is changing altitudes
     public int upSpeed = 24;                        // Maximum Speed when pulling back on stick; pitching up
     private bool slerped;                            // bool to prevent double slerping
     
     public float roll;                                // amount to rotate on the z axis
     public float pitch;                                // amount to rotate on the x axis
     
     public float rollAngle;                            // amount the glider model has rotated on the z axis.
     public float pitchAngle;                        // amount the glider model has rotated on the x axix.
     private float maxPitch = 0.15f;                    // maximum angle to pitch model
     private float maxRoll = 0.35f;                    // maximum angle to roll model.
             
     private Vector3 moveDirection = Vector3.zero;    // x y z movement amounts
     public CharacterController controller;            // the character controller
     private Transform playerModel;                    // the model or parent of the model. child of object containing controller.
 
     // Use this for initialization
     void Start () {
         controller = GetComponent<CharacterController>();
         playerModel = transform.FindChild("PlayerModel");
     }    
     
     // Update is called once per frame
     void Update () {
         slerped = false;
         roll = pitch = 0;
         
         // Prevent Slerp when pitching or rolling
         if(Input.GetAxis("Horizontal") != 0) rolling = true;
         if(Input.GetAxis ("Vertical") != 0) pitching = true;
         
         // Roll Right when player stears right if roll angle doesnt exceed max roll
         if( (rollAngle + (Input.GetAxis("Horizontal") * rollSpeed * Time.deltaTime) < maxRoll) && Input.GetAxis("Horizontal") > 0){
                 roll = Input.GetAxis("Horizontal") * rollSpeed * Time.deltaTime;
                 rollAngle += Input.GetAxis("Horizontal") * rollSpeed * Time.deltaTime;
         }
                 
         // Roll Left when player stears left if roll angle doesnt exceed max roll
         if( (rollAngle + (Input.GetAxis("Horizontal") * rollSpeed * Time.deltaTime) > -maxRoll) && Input.GetAxis("Horizontal") < 0){
                 roll = Input.GetAxis("Horizontal") * rollSpeed * Time.deltaTime;
                 rollAngle += Input.GetAxis("Horizontal") * rollSpeed * Time.deltaTime;
         }
         
         // Pitch Back when player pulls back if pitch angle doesnt exceed max pitch and slow speed
         if( (pitchAngle + (Input.GetAxis("Vertical") * pitchSpeed * Time.deltaTime) < maxPitch) && Input.GetAxis("Vertical") > 0){
                 pitch = Input.GetAxis("Vertical") * pitchSpeed * Time.deltaTime;
                 pitchAngle += Input.GetAxis("Vertical") * pitchSpeed * Time.deltaTime;
                 altitudeChangeSpeed = Mathf.Lerp(altitudeChangeSpeed, 10, 0.1f);
                 if(moveSpeed - 1 >= upSpeed)
                     moveSpeed--;        
         }
         
         // Pitch Forward when player pushed forward if pitch angle doesnt exceed max pitch and increase speed
         if( (pitchAngle + (Input.GetAxis("Vertical") * pitchSpeed * Time.deltaTime) > -maxPitch) && Input.GetAxis("Vertical") < 0){
                 pitch = Input.GetAxis("Vertical") * pitchSpeed * Time.deltaTime;
                 pitchAngle += Input.GetAxis("Vertical") * pitchSpeed * Time.deltaTime;
                 altitudeChangeSpeed = Mathf.Lerp(altitudeChangeSpeed, -10, 0.1f);
                 if(moveSpeed + 1 <= maxSpeed)
                     moveSpeed++;        
         }
         
         // Roll Back towards neutral when player not turning. Slerp when not pitching or rolling.
         if( Input.GetAxis("Horizontal") == 0 ){
             if( rollAngle - (0.5f * rollSpeed * Time.deltaTime) > 0 ){
                 roll = 0.5f * -rollSpeed * Time.deltaTime;
                 rollAngle -= 0.5f * rollSpeed * Time.deltaTime;
             } else if( rollAngle + (0.5f * rollSpeed * Time.deltaTime) < 0 ){
                 roll = 0.5f * rollSpeed * Time.deltaTime;
                 rollAngle += 0.5f * rollSpeed * Time.deltaTime;
             } else if(Input.GetAxis("Vertical") == 0 && Input.GetAxis("Horizontal") == 0){
                 playerModel.rotation = Quaternion.Slerp (playerModel.rotation, transform.rotation, Time.deltaTime * rollSpeed);
                 slerped = true;
             }
         }
         
         // Pitch Back towards neutral when player not pitching. Slerp when not pitching, rolling or slerping in horizontal.
         if( Input.GetAxis("Vertical") == 0 ){
             altitudeChangeSpeed = Mathf.Lerp(altitudeChangeSpeed, -6, 0.1f);
             
             // Ramp up to glide speed
             if(moveSpeed < glideSpeed)
                 moveSpeed += moveSpeed * Time.deltaTime;                                    
             if(moveSpeed > glideSpeed)
                 moveSpeed = glideSpeed;    
             
             if( pitchAngle - (0.5f * pitchSpeed * Time.deltaTime) > 0 ){
                 pitch = 0.5f * -pitchSpeed * Time.deltaTime;
                 pitchAngle -= 0.5f * pitchSpeed * Time.deltaTime;
             } else if( pitchAngle + (0.5f * pitchSpeed * Time.deltaTime) < 0 ) {
                 pitch = 0.5f * pitchSpeed * Time.deltaTime;
                 pitchAngle += 0.5f * pitchSpeed * Time.deltaTime;
             } else if (!slerped && Input.GetAxis("Vertical") == 0 && Input.GetAxis("Horizontal") == 0)
                 playerModel.rotation = Quaternion.Slerp (playerModel.rotation, transform.rotation, Time.deltaTime * rollSpeed);
         }
         
         // set move direction from speeds
         moveDirection = new Vector3( 0, altitudeChangeSpeed, moveSpeed );
         
         // roll and pitch child.
         playerModel.RotateAroundLocal(Vector3.forward, -roll);
         playerModel.RotateAroundLocal(Vector3.right, -pitch);
         
         //transform direction
         moveDirection = transform.TransformDirection(moveDirection);
         
         // rotate transform when turning
         transform.Rotate(0 , Input.GetAxis("Horizontal") * turnSpeed * Time.deltaTime, 0, 0);
         
         // move controller
         controller.Move(moveDirection * Time.deltaTime);
     }
 }
Comment
Add comment · Share
10 |3000 characters needed characters left characters exceeded
▼
  • Viewable by all users
  • Viewable by moderators
  • Viewable by moderators and the original poster
  • Advanced visibility
Viewable by all users

Your answer

Hint: You can notify a user about this post by typing @username

Up to 2 attachments (including images) can be used with a maximum of 524.3 kB each and 1.0 MB total.

Follow this Question

Answers Answers and Comments

14 People are following this question.

avatar image avatar image avatar image avatar image avatar image avatar image avatar image avatar image avatar image avatar image avatar image avatar image avatar image avatar image

Related Questions

How can I multiply the rotation of a mirrored object? 1 Answer

How do you manually override mecanim's interpolation with rotations? 2 Answers

Rotate an object around z axis on user input 1 Answer

Get pitch and roll 0 Answers

finding pitch/roll/yaw from Quaternions 4 Answers


Enterprise
Social Q&A

Social
Subscribe on YouTube social-youtube Follow on LinkedIn social-linkedin Follow on Twitter social-twitter Follow on Facebook social-facebook Follow on Instagram social-instagram

Footer

  • Purchase
    • Products
    • Subscription
    • Asset Store
    • Unity Gear
    • Resellers
  • Education
    • Students
    • Educators
    • Certification
    • Learn
    • Center of Excellence
  • Download
    • Unity
    • Beta Program
  • Unity Labs
    • Labs
    • Publications
  • Resources
    • Learn platform
    • Community
    • Documentation
    • Unity QA
    • FAQ
    • Services Status
    • Connect
  • About Unity
    • About Us
    • Blog
    • Events
    • Careers
    • Contact
    • Press
    • Partners
    • Affiliates
    • Security
Copyright © 2020 Unity Technologies
  • Legal
  • Privacy Policy
  • Cookies
  • Do Not Sell My Personal Information
  • Cookies Settings
"Unity", Unity logos, and other Unity trademarks are trademarks or registered trademarks of Unity Technologies or its affiliates in the U.S. and elsewhere (more info here). Other names or brands are trademarks of their respective owners.
  • Anonymous
  • Sign in
  • Create
  • Ask a question
  • Spaces
  • Default
  • Help Room
  • META
  • Moderators
  • Explore
  • Topics
  • Questions
  • Users
  • Badges