Search Unity

rotate parent object so that a child object faces the camera

Discussion in 'Scripting' started by _OK_, Jun 18, 2019.

  1. _OK_

    _OK_

    Joined:
    Oct 3, 2014
    Posts:
    33
    hi

    struggling to get this to work, tried loads of variations of rotations. I have sphere(planet) with a child object (marker) on it. what I would like to do is rotate the sphere so that the marker looks at the camera.

    Any ideas? thank so much
     
  2. xVergilx

    xVergilx

    Joined:
    Dec 22, 2014
    Posts:
    1,906
    Make sure your marker is placed / aligned with the forward (blue) axis of the sphere (in local mode) initially;

    Then do something like:
    Code (CSharp):
    1. Transform sphereTrm = sphere.transform;
    2. Transform camTrm = // grab a camera transform however you like;
    3.  
    4. sphereTrm.forward = (sphereTrm.position - camTrm.position).normalized;
    5.  
    6. // Might be reversed order, e.g. camTrm.position - sphereTrm.position
     
    Last edited: Jun 18, 2019
  3. _OK_

    _OK_

    Joined:
    Oct 3, 2014
    Posts:
    33
    hi thanks for that
    wouldn't this just point the sphere towards the camera? the marker is placed on the surface of the sphere with its forward pointing straight out.
     
  4. xVergilx

    xVergilx

    Joined:
    Dec 22, 2014
    Posts:
    1,906
    If you place your marker along forward axis of the sphere, sphere will rotate its forward pointing towards the camera.
    Which will make your sphere pointing marker to the camera.

    If you want your marker to be pointing towards camera as well, do the same thing but on the marker transform.

    Alternatively, you can place marker at certain distance along direction to the camera from the center of the sphere. And point it towards the camera afterwards.
    (In case you do not want sphere to be rotated at all)
    Code (CSharp):
    1. // Something like this
    2. [SerializeField]
    3. private float _distanceFromSphere = 1f;
    4.  
    5. [SerializeField]
    6. private Transform _markerTrm;
    7.  
    8. [SerializeField]
    9. private Trasnform _sphereTrm;
    10.  
    11. // Upon some action or update
    12. Vector3 direction = (_sphereTrm.position - camTrm.position).normalized); // Potentially in a reverse order if I screwed up;
    13.  
    14. // Shift from the sphere center towards camera direction
    15. _markerTrm.position = _sphereTrm.position + direction * _distanceFromSphere;
    16.  
    17. // Align marker forward to the sphere -> camera direction
    18. _markerTrm.forward = direction;
     
    Last edited: Jun 18, 2019
  5. _OK_

    _OK_

    Joined:
    Oct 3, 2014
    Posts:
    33
    the marker can be placed anywhere on the sphere, i don't want the sphere to face the camera based on the spheres forward, I'm trying to position the marker centrally in the view of the camera by rotating the entire sphere. the rotation needs to be based on the markers position/forward not the sphere.

    does that make sense?
     
  6. WallaceT_MFM

    WallaceT_MFM

    Joined:
    Sep 25, 2017
    Posts:
    264
    Try something along these lines:
    1. Get the rotation from the marker to the sphere's z-axis. Note that the direction matters.
    2. Rotate the sphere's z-axis towards the camera.
    3. Rotate the sphere by the rotation found in 1.
    You can combine step's 2 and 3 to find the sphere's new target rotation, which will point the marker at the camera.
     
    xVergilx likes this.
  7. xVergilx

    xVergilx

    Joined:
    Dec 22, 2014
    Posts:
    1,906
    Simplest solution to this is to parent sphere to the marker instead of parenting marker to the sphere.
    Then align the marker to point towards the camera. Sphere will rotate as well.

    Hardest / hackiest - determine current rotation difference between sphere and marker.
    Then rotate the marker to be aligned to the camera.
    Rotate the sphere to that difference.
    Realign the marker.
    (kinda posted above);
     
  8. _OK_

    _OK_

    Joined:
    Oct 3, 2014
    Posts:
    33
    thanks for the posts, I appreciate it. Answer of how I did it below should it help some else.

    in the end I fixed it by rotating the camera around the sphere using a standard orbit camera script. I just put the x and y position of the marker in the script and it centres the marker on the screen.


    place marker on sphere using the latitude and longitude coordinates

    Code (CSharp):
    1. transform.localPosition = Quaternion.AngleAxis(longG, -Vector3.up) * Quaternion.AngleAxis(-lat, -Vector3.right) * new Vector3(0,0,altitude);
    placed this script in update on camera pot is vector3, rot is Quaternion

    Code (CSharp):
    1.  
    2.        // x += Input.GetAxis("Mouse X") * xSpeed * 0.02f;
    3.       //  y -= Input.GetAxis("Mouse Y") * ySpeed * 0.02f;
    4.        // y = ClampAngle(y, yMinLimit, yMaxLimit);
    5.         rot= Quaternion.Euler(currentTarget.lat, -currentTarget.longG, 0f);
    6.         pot = rot * new Vector3(0.0f, 0.0f, -distance) + Target.transform.position;
    7.         transform.rotation = rot;
    8.         transform.position = pot;
     
  9. Joe-Censored

    Joe-Censored

    Joined:
    Mar 26, 2013
    Posts:
    6,340
    You could consider doing this silly idea:

    1) Make the marker the parent of the sphere
    2) Use LookAt on the marker to align to the camera
    3) Make the marker a child of the sphere
     
  10. SparrowsNest

    SparrowsNest

    Joined:
    Apr 6, 2017
    Posts:
    1,837
    I don't think the marker parent is really good, in my eyes the planet can have many markers on him making this a bit of a hassle instead of calculating the wanted rotation like the OP wanted.

    Give me a couple of minutes and i'll get back to you on that, I wanna test what I have in my head.

    edit: I was sure I was gonna get it in 10-15 minutes using Quaternion.FromToRotation, guess not, heh

    what I tried was getting the direction from planet center to marker, get direction from planet center to camera, calculate the offset between them and apply it to the planet rotation.
    I still think this should work, I must have gotten my maths wrong, I'm just having my morning tea so I may come back to this later.
     
    Last edited: Jun 19, 2019
  11. _OK_

    _OK_

    Joined:
    Oct 3, 2014
    Posts:
    33
    I did the same some time back - tbh it sounds so simple but maths is not my strong point - the way I solved it works perfectly and has the added advantage that the planet doesn't rotate on its z axis so its easier to manually rotate it to allow placement of markers.

    I'd still be interested to know how its done anyway - if some one can do it
     
  12. halley

    halley

    Joined:
    Aug 26, 2013
    Posts:
    729
    I betcha you ordered your Quaternion multiplies backwards. That's what always trips me up.
     
  13. palex-nx

    palex-nx

    Joined:
    Jul 23, 2018
    Posts:
    1,171
    That should be easy. Calculate rotation Q1 for sphere to point it's forward vector to camera. Calculate rotation Q2 from marker.position - sphere.position) to camera.forward. Now calculate Q3 = Q1 * Q2 and this will be desired rotation.

    Remember, there are many sphere rotations possible for sphere to face particular position on it to camera.
     
  14. blamejane

    blamejane

    Joined:
    Jul 8, 2013
    Posts:
    209
    I'm having this same problem as OP. Just curious if you could elaborate on the actual order of the Quaternion multiples? That is, could you show the correct order if you think the OP did it backwards?

    Thanks.