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 Malactus · Feb 18, 2013 at 11:10 AM · mathprocedural generationquaternionsrotations

Relative Rotations and Position calculation

I'm currently working on a random level generator prototype that uses templates blocks with a child object EntryPoint.

The EntryPoint behaves as a potential point at which the next chunk of the level is loaded to as a child.

Its a bit difficult to explain directly for me with words and by default is a challenge to solve, But I'm having issues with rotations and positions relative to these points:


To help me explain, here is a scenario I'm currently using to Dev this:

There will be three prefabs, lets call them A, B, C.

A and C are both connected to B when the level is generated.

A has 1 EntryPoint, Ill call it A1. It is a room with a single entrance/exit. B has 2 EntryPoints, Ill call them B1, B2. It could be a corner, staircase, which ever. C has 1 EntryPoint, Ill call them C1. It is a room with a single entrance/exit.

As of the moment, when the level generates,

  • A1 will spawn B as a child of it

  • B translates so that either B1 or B2 is facing the opposite direction of A1

  • The Next Free EntryPoint will then spawn C as a child to the EntryPoint

  • C translates so that C1 is on the Free EntryPoint

As a summary EntryPoints behave as an 'attachment point' for the level to generate upon.

The current issue is that the calculated rotations and offsets are as completely incorrect. While I know how to do Initiate the child object, the issue comes with relative rotations so that the entry points match as opposites.

Could anyone give me pointers on how I should calculate the points?

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

2 Replies

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

Answer by Malactus · Feb 18, 2013 at 05:26 PM

Aaaand I Solved this. (Dunno maybe next time I should wait for 24 hours before asking a question, as it takes a good while for a question to be accepted as a question but these sort of odd rotation issues seem to occur)

Luckily I'm stubborn enough to just keep trying to approach a solution until I solve it, or simply give up after a few days.

As reference to others:

Instead of moving by transform.position, and transform.rotation, I used the inherit method transform.Translate and transform.Rotate, which rotate the object by its own reference. So Barely any math needed.

So after Initiating with the rotation and position of the spawning EntryPoint, I then use these to move and rotate so that the points match the opposite of each other.

 // Game Object Intantiate
         this.setUsed( true );
         brush = GameObject.Instantiate(tileEntity,  this.transform.position, this.transform.rotation ) as GameObject;
         // Get Available Entry Points
         entryPoints = brush.GetComponentsInChildren<EntryPoint>();
                 
         if(entryPoints != null){ //
             
             // Select Random entry Point
             EntryPoint selectedEntry = entryPoints[ Random.Range(0, entryPoints.Length)];
             selectedEntry.gizmoColor = this.gizmoColor * 0.8f; // Debug Color
             
             selectedEntry.setUsed(true);
             
             Vector3 eulerRotation = Quaternion.Inverse(selectedEntry.transform.localRotation).eulerAngles;
             eulerRotation.y += 180; // Locally rotate 180 on y. Its the opposite to result y
             brush.transform.Rotate(eulerRotation); 
             
             brush.transform.Translate( -selectedEntry.transform.localPosition); // Relative to self, move 

         // TODO: prolly garbage collect here later to remove unnecessary
         }else{
             throw UnityException("Gameobject " +brush + " does not contain any entries" );    
         }
 
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
avatar image
1

Answer by aldonaletto · Feb 18, 2013 at 05:29 PM

You must first rotate the new block so that its EntryPoint is facing the EntryPoint to which it must connect, then calculate the block offset. All EntryPoints must obey a consistent orientation rule - the forward direction of each EntryPoint points outside the block, for instance.
You could use Instantiate(newBlock) to create a new block without worrying about its position and rotation, then adjust it with a function like below, where ep1 is the reference EntryPoint and ep2 is the new block's EntryPoint:

 function AlignNewBlock(ep1: Transform, ep2: Transform){
   // find relative rotation that makes ep2 face ep1:
   var rot: Quaternion = Quaternion.FromToRotation(ep2.forward, -ep1.forward);
   // convert the rotation to parent space:
   rot = rot * Quaternion.Inverse(ep2.localRotation);
   // rotate the ep2 parent:
   var block: Transform = ep2.parent;
   block.rotation *= rot;
   // find offset of new block relative to ep2:
   var offset: Vector3 = block.position - ep2.position;
   // position block so that ep2 is at ep1 position:
   block.position = ep1.position + offset;
 }

NOTE: I've not tested this, thus let me know if something is wrong.

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

10 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

Related Questions

Quaternions rotating left and right, not forward and back 1 Answer

Problem with Windswept Procedural tree 1 Answer

My interpretation of Random.rotation and Random.rotationUniform. Right or wrong ? 0 Answers

How to use quaternions to apply an offset to a rotation to calibrate a controller 1 Answer

Endless racer - positioning of track segments 0 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