Wednesday, September 13, 2017

Throwing things in a perfect circle

How difficult do you think it can be to throw things in a circle?
Not as easy as you'd think or I'd like.
It took me 2-3 hours to figure the following tiny chunk of code. AND I have the background. Shit. Maybe I am just bad at what I'm doing, lol. Anyway, it felt like it was worth a short blog post.

var texts = array of things to throw around;
var count = texts.Length;
var circularUIRadius = how far to throw from the central point;
var depthUI = how close to the target object things should be;

//So here it starts - the target object position:
var targetCenter = Vector3.Lerp(this.transform.position, Camera.main.transform.position, depthUI);

//I want to get the direction vector from the target to the camera. What can be easier?
Vector3 facingCamera = (Camera.main.transform.position - targetCenter).normalized;

//Make sure things are happening as I think they are:
Debug.DrawRay(targetCenter, facingCamera, Color.blue, 5.0f, false);

//Here starts the fun - get the second vector to describe the plane, into which the circle of texts goes
//The first axis is Vector3.up, but this can still be improved totilt the plane up or down depending if the camera moves up or down. <TO BE DONE>
var directionPerpendicular = Vector3.Cross(facingCamera, Vector3.up).normalized; -// --> this didn't work! Quaternion.Euler(0, -90, 0) * direction;
Debug.DrawRay(targetCenter, directionPerpendicular, Color.yellow, 5.0f);

for (var i = 0; i < count; i++)
{

  // super advanced spatial geometry math from parametric-equation-of-a-circle-in-3d-space
  //Get the desired angle for the thing, we strive for equality and symmetry
  var angle = Math.PI * i * 2 / count;
  //Calculate the final location for the text
  var target = targetCenter + circularUIRadius * (float)Math.Cos(angle)*Vector3.up + circularUIRadius * (float)Math.Sin(angle)*directionPerpendicular; 
  texts[i].transform.position = target;

  //And the final touch - cherry, so to say...                    
  // rotate to camera - prevent text from being mirrored from lookat-in-opposite-direction
  texts[i].transform.LookAt(2*target - Camera.main.transform.position);
}




Result!
 


No comments:

Post a Comment