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
2
Question by Chris42 · Apr 13, 2011 at 06:45 PM · rotationaxisclampturretrestrict

Constraining turret rotation in local space

Ok, I've been banging my head against the wall for a while with this. My understanding of quaternions and rotations is poor at best, so I'm looking to get some input.

Essentially, I have a physically simulated player-controlled spaceship (in full3d space) with a bunch of turrets all over it. These are aimed around at an aim target box which changes location based on mouse position. So far so good - I can aim my turrets pretty well.

However, my turrets need to be constrained, so that the base only rotates (yaws) and the barrel only pitches. Additionally, there should be some way to constrain these rotations so that a turret doesn't point, say, into the ship.

This is how it works right now: On start, I set up the turret by getting its local rotations in the rest position.

function Start() { rb = rigidbody;

 // set up barrel and muzzle
 for (var child : Transform in turretBody) {
     turretBarrel = child;
 }
 for (var child : Transform in turretBarrel) {
     turretMuzzle = child;   
 }

 // set up base turret orientation
 turretXLocked = turretBody.localRotation.eulerAngles.x;
 turretZLocked = turretBody.localRotation.eulerAngles.z;

 barrelYLocked = turretBarrel.localRotation.eulerAngles.y;
 barrelZLocked = turretBarrel.localRotation.eulerAngles.z;

 print (turretXLocked);
 print (turretZLocked);

}

I then run this in Update:

function Update() {

 AimTurretBase();
 AimTurretBarrel();

 if(Input.GetMouseButton(0) && timer == 0) {

      PlayMuzzleFX(turretMuzzle.position,turretMuzzle.rotation);
      FireWeapon(turretMuzzle.position,turretMuzzle.rotation);
      StartReloadTimer();        
 }

}

I'll just post AimTurretBase here as AimTurretBarrel is essentially the same.

So here I get my AimTarget and turret base position, then create a rotation to point the turret at it. Then I rotate the turret, but set the X and Z rotation to zero so that it only rotates in the Y space.

function AimTurretBase() { var origPos:Vector3 = turretBody.position; var targetPos:Vector3 = aimTarget.position; var rotGoal = Quaternion.LookRotation(targetPos - origPos);

 var actualGoal = rotGoal;
 var curRot = Quaternion.Slerp(turretBody.rotation,actualGoal,Time.deltaTime*turretTurnRate);

 // always clamp the turret to the ship
 turretBody.localRotation.eulerAngles.z = turretZLocked;
 turretBody.localRotation.eulerAngles.x = turretXLocked;

}

So this... kinda works. If the turret is in the same axal plane as the ship, flawless clamping of the turret to the ship occurs. However, if i rotate the turret so it's on an angle, like on the side of the ship, it breaks down. I have been debugging for a while and have no clue why - I suspect my method is somehow flawed.

So Question 1: how do I lock an object's rotation in some axes to a ship?

Then we also have Question 2: once that's done, how can I limit the axis that is free such that it can only rotate, say, 60 degrees in either direction?

Oh, and I'd rather not use joints. Mainly because I want to get good at this stuff and that's the easy way out.

Help is super appreciated!

Comment
Add comment
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

1 Reply

· Add your reply
  • Sort: 
avatar image
1
Best Answer

Answer by synapsemassage · Apr 13, 2011 at 07:14 PM

localRotation is relative to the parent. I guess the parent for your turret is the ship? Placing your turret on your ship by moving and rotating will change its localPosition and localRotation relative to the ship. A simple workaround should be an empty GameObject as a dummy with the turret as child. Create the dummy at same position/rotation like the turret in its default position/rotation. The turrets localRotation will be relative to the dummy. When placing the dummy on the ship the turret should rotate correctly. Make the dummy a child of the ship: ship/dummy/child.

Quaternions are not intuitive at all, a PIA. The whole rotation thing is not intuitive, even not with Unity ;-). As space doesn't care about orientation but humans do,it's a good idea to think in reference systems, means the dummy is your reference system to orient your object relatively.

Try calling AimTurretBase() + AimTurretBarrel() also(!) in Start().

var rb:Rigidbody; var child:Transform; var turretMuzzle:Transform;

function Start(){ // set up barrel and muzzle for (child in turretBody) { turretBarrel = child; } for (child in turretBarrel) { turretMuzzle = child; }

// set up base turret orientation turretXLocked = turretBody.localRotation.eulerAngles.x; turretZLocked = turretBody.localRotation.eulerAngles.z; barrelYLocked = turretBarrel.localRotation.eulerAngles.y; barrelZLocked = turretBarrel.localRotation.eulerAngles.z;

AimTurretBase(); AimTurretBarrel(); }

BTW avoid dynamic typing for performance reasons: "var rotGoal" should be "var rotGoal:Quaternion". Also prefer for performance reasons defining variables outside Update-related functions like:

var origPos : Vector3; var targetPos : Vector3; var rotGoal : Quaternion; var actualGoal : Quaternion;

function AimTurretBase(); { origPos = turretBody.position; targetPos = aimTarget.position; rotGoal = Quaternion.LookRotation(targetPos - origPos);

// and so on

}

Comment
Add comment · Show 5 · 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
avatar image Chris42 · Apr 14, 2011 at 03:56 AM 0
Share

This seems to help significantly, thanks! Now the turrets rotate correctly. They don't, however, aim correctly anymore - though each turret is supposed to point at the aimTarget, they point at slightly different locations around it

Presumably this is due to the change in reference positions... my previous code looked from turretBody.position to aimTarget. position in world space. so would I now want to move aimTarget into local space, then point the local rotation at that?

If so, how do I do that?

avatar image synapsemassage · Apr 16, 2011 at 09:42 PM 0
Share

Not sure if I got you right, actually I expected it to work. What do you mean with "slightly different positions around it", almost pointing correctly at the target? Are you sure that dummy and turret were at (0,0,0) on creation?

avatar image Chris42 · Apr 17, 2011 at 08:03 AM 0
Share

I checked the zeros and did some debugging, everything is zeroes and seems fine. A more precise description is that the bottom turrets get to the target eventually, but they overshoot and have to track back. The top ones don't do this.

avatar image synapsemassage · Apr 18, 2011 at 01:37 PM 0
Share

Try calling AimTurretBase() + AimTurretBarrel() also(!) in Start(). see above.

avatar image Chris42 · Apr 18, 2011 at 11:40 PM 0
Share

D'oh! $$anonymous$$y barrel wasn't restricted, and had a faster turn rate than the turret, so the barrel was 'helping' turn on the y-axis. Of course, it overshot and the attempts at correction resultingly just caused an oscillation.

Thanks for the help!

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

No one has followed this question yet.

Related Questions

Slerp Z and X axis only 1 Answer

Constraints on rotation axis in c# 1 Answer

How to rotate cannon by angles on top of a turret 1 Answer

itween path restrict rotation on TWO axis 0 Answers

Help clamping a Rotation 1 Answer


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