创建一条曲线以显示对象在 Unity 中的投影位置

Create a curve to show where an object will be projected in Unity

我在下面有一些代码,可以沿着曲线将对象投影到给定位置,并且效果很好。

using System.Collections;
using System.Collections.Generic;
using UnityEngine;

public class Move : MonoBehaviour {

    public GameObject platform;
    public Vector3 targetPos;
    public float speed = 10;
    public float arcHeight = 1;

    Vector3 startPos;

    GameObject line;


    // Use this for initialization
    void Start () {
        startPos = transform.position;
        targetPos = platform.transform.position;
        targetPos.x -= 0.7f;
        targetPos.y += 1.5f;
    }

    // Update is called once per frame
    void Update () {
       movePlayer();
    }


    void movePlayer()
    {
        // Compute the next position, with arc added in
        float x0 = startPos.x;
        float x1 = targetPos.x;
        float dist = x1 - x0;
        float nextX = Mathf.MoveTowards(transform.position.x, x1, speed * Time.deltaTime);
        float baseY = Mathf.Lerp(startPos.y, targetPos.y, (nextX - x0) / dist);
        float arc = arcHeight * (nextX - x0) * (nextX - x1) / (-0.25f * dist * dist);
        Vector3 nextPos = new Vector3(nextX, baseY + arc, transform.position.z);


        transform.position = nextPos;

        // Do something when we reach the target
        if (nextPos == targetPos) Arrived();
    }

    void Arrived()
    {
        Destroy(gameObject);
    }

}

我现在希望能够添加一条可见的曲线来显示对象的路径。我看过一些使用 LineRenderer 的示例,但我不确定如何将其合并到我移动对象的方式中。任何有关如何执行此操作的帮助将不胜感激。

我编辑了您的代码,让 LineRenderer 创建路径。这个想法是您预先生成对象的坐标,使用一个位置作为下一个位置的输入。 (所以不仅仅取决于对象的变换)。

一定要在检查器中设置一个Material,否则你只会看到一条粉红色的线。我希望这是你想要的。

using System.Collections;
using System.Collections.Generic;
using UnityEngine;

public class Move : MonoBehaviour
{

    public GameObject platform;
    public Vector3 targetPos;
    public float speed = 10;
    public float arcHeight = 1;

    Vector3 startPos;

    GameObject line;

    /// <summary>
    /// Our linerenderer
    /// </summary>
    private LineRenderer lineRenderer;

    /// <summary>
    /// Line material.
    /// </summary>
    [SerializeField]
    private Material lineMaterial;

    // Use this for initialization
    private void Start()
    {
        startPos = transform.position;
        targetPos = platform.transform.position;
        targetPos.x -= 0.7f;
        targetPos.y += 1.5f;

        // Add a linerenderer.
        lineRenderer = gameObject.AddComponent<LineRenderer>();

        if (lineMaterial == null)
        {
            Debug.LogError("No LineMaterial specified!");
        }

        // If you do not want to use worldspace, set this to false:
        lineRenderer.useWorldSpace = true;

        // Set preferred texture mode for texture.
        lineRenderer.textureMode = LineTextureMode.RepeatPerSegment;

        // Shadows, or not?
        //lineRenderer.shadowCastingMode = UnityEngine.Rendering.ShadowCastingMode.Off;
        //lineRenderer.receiveShadows = false;

        // Finally, set the material that you want to assign.
        // Remember: If you use default shader, it needs to be set to "Transparent" to get your texture's alpha working.
        lineRenderer.sharedMaterial = lineMaterial;


    }

    // Update is called once per frame
    private void Update()
    {
        movePlayer();
    }

    private void movePlayer()
    {
        // Compute the next position, with arc added in
        Vector3 nextPos = newPosition(transform.position, speed * Time.deltaTime);
        transform.position = nextPos;

        // Calculate upcoming positions.
        Vector3[] points = generateUpcomingPositions(nextPos);
        CreateLine(points);


        // Do something when we reach the target
        if (nextPos == targetPos) Arrived();
    }

    private Vector3 newPosition(Vector3 currentPosition, float delta)
    {
        float x0 = startPos.x;
        float x1 = targetPos.x;
        float dist = x1 - x0;
        float nextX = Mathf.MoveTowards(currentPosition.x, x1, delta);
        float baseY = Mathf.Lerp(startPos.y, targetPos.y, (nextX - x0) / dist);
        float arc = arcHeight * (nextX - x0) * (nextX - x1) / (-0.25f * dist * dist);
        Vector3 nextPos = new Vector3(nextX, baseY + arc, currentPosition.z);

        return nextPos;
    }

    private Vector3[] generateUpcomingPositions(Vector3 currentPosition)
    {
        int steps = 10;
        float delta = (1.0f / ((steps - 1))) * 2.0f;// Double delta.
        List<Vector3> points = new List<Vector3>();

        Vector3 newPos = currentPosition;
        for (int i = 0; i < steps; i++)
        {
            // Use newPos as input for location.
            newPos = newPosition(newPos, delta * i);

            points.Add(newPos);
        }

        return points.ToArray();
    }


    private void Arrived()
    {
        Destroy(gameObject);
    }

    /// <summary>
    /// Create a line with a given name, width and points.
    /// </summary>
    /// <param name="points"></param>
    private void CreateLine(Vector3[] points)
    {

        // Set the positions.
        lineRenderer.positionCount = points.Length;
        lineRenderer.SetPositions(points);

    }
}