Make object visual size constant despite the dista

2019-08-19 03:15发布

问题:

Visual aid here

Please see visual aid. Following the gif, there are two GUIs. The GUI on the left is scaling properly based on the cameras distance to the object. The GUI on the right is scaling, seen clearly in the 'Scene' view, but not even noticeable in game view. The application is for the Hololens as the users head controls the camera within the Unity scene.

The problem lies in setting the objects scaling. Been racking my brain all day trying to replicate the type of scaling shown on the left GUI. Dividing the distance and using this as the factor to scale by is clearly incorrect as the object is either far too large and grows too fast, or far too small and grows too slowly but I don't know how to meet somewhere in the middle. Scaling in both directions equally at a noticeable yet not obnoxiously large or imperceptible rate.

Implementation code thus far:

// GameObject and GUI assigned in Editor
public GameObject sphere, rotationManager;

// For rotationManager scaling
private float cameraToObject,

void Update()
{
    /* Scale rotationManager based on Cameras distance to object */
    cameraToObject = Vector3.Distance(
        sphere.transform.position, 
        Camera.main.transform.position);

    Debug.Log("distance: " + cameraToObject);

    // If camera isn't too close to our object
    if (cameraToObject > 4f)
    {
        // adjust scale
        rotationManager.transform.localScale = new Vector3(
            cameraToObject / 5, 
            cameraToObject / 5, 
            rotationManager.localScale.z);

        // enable rotationManager
        rotationManager.gameObject.SetActive(true);

    }
    // Camera is too close, turn off GUI
    else
        rotationManager.gameObject.SetActive(false);
}

回答1:

Not really sure what you are doing wrong, as dividing distance by constant must give required effect. Anyway try this code:

using UnityEngine;

public class AutoSize : MonoBehaviour
{
    public float FixedSize = .005f;
    public Camera Camera;

    void Update ()
    {
        var distance = (Camera.transform.position - transform.position).magnitude;
        var size = distance * FixedSize * Camera.fieldOfView;
        transform.localScale = Vector3.one * size;
        transform.forward = transform.position - Camera.transform.position;
    }
}

It seems to work fine - preview

Also maybe it will be more effective to create constant menu size and just position it by converting world space to the screen space.