Example #1
0
    /// <summary>
    /// Ensures the mesh data for the renderer is created, and updates it if neccessary
    /// </summary>
    /// <param name="force">Whether or not to force a full rebuild of the mesh data</param>
    /// <returns>True if an initialization occurred, false if it was skipped</returns>
    protected bool Initialize(bool force = false)
    {
        if (m_Positions == null)
        {
            return(false);
        }
        var performFullInitialize = force;

        // For a line renderer we assume one big chain
        // We need a control point for each billboard and a control point for each pipe connecting them together
        // Except for the end, which must be capped with another billboard.  This gives us (positions * 2) - 1
        var neededPoints = Mathf.Max((m_Positions.Length * 2) - 1, 0);

        if (m_MeshData == null)
        {
            m_MeshData = new VRLineRendererInternal.MeshChain();
        }
        if (m_MeshData.reservedElements != neededPoints)
        {
            m_MeshData.worldSpaceData = useWorldSpace;
            m_MeshData.GenerateMesh(gameObject, true, neededPoints);
            performFullInitialize = true;
        }
        if (performFullInitialize == false)
        {
            return(false);
        }
        if (neededPoints == 0)
        {
            return(true);
        }

        var pointCounter   = 0;
        var elementCounter = 0;

        // Initialize the single starting point
        m_MeshData.SetElementSize(elementCounter, m_WidthStart);
        m_MeshData.SetElementPosition(elementCounter, ref m_Positions[pointCounter]);
        m_MeshData.SetElementColor(elementCounter, ref m_ColorStart);
        elementCounter++;
        pointCounter++;

        float stepSize    = 1.0f / Mathf.Max((m_Positions.Length - 1.0f), 1.0f);
        float stepPercent = stepSize;
        var   lastWidth   = m_WidthStart;
        var   lastColor   = m_ColorStart;

        // Now do the chain
        while (pointCounter < m_Positions.Length)
        {
            var currentWidth = Mathf.Lerp(m_WidthStart, m_WidthEnd, stepPercent);
            var currentColor = Color.Lerp(m_ColorStart, m_ColorEnd, stepPercent);

            // Create a pipe from the previous point to here
            m_MeshData.SetElementSize(elementCounter, lastWidth, currentWidth);
            m_MeshData.SetElementPipe(elementCounter, ref m_Positions[pointCounter - 1], ref m_Positions[pointCounter]);
            m_MeshData.SetElementColor(elementCounter, ref lastColor, ref currentColor);
            elementCounter++;

            // Now record our own point data
            m_MeshData.SetElementSize(elementCounter, currentWidth);
            m_MeshData.SetElementPosition(elementCounter, ref m_Positions[pointCounter]);
            m_MeshData.SetElementColor(elementCounter, ref currentColor);

            // Go onto the next point while retaining previous values we might need to lerp between
            lastWidth = currentWidth;
            lastColor = currentColor;
            elementCounter++;
            pointCounter++;
            stepPercent += stepSize;
        }

        // Dirty all the MeshChain flags so everything gets refreshed
        m_MeshData.SetMeshDataDirty(VRLineRendererInternal.MeshChain.MeshRefreshFlag.All);
        m_MeshNeedsRefreshing = true;
        return(true);
    }
    /// <summary>
    /// Ensures the mesh data for the renderer is created, and updates it if neccessary
    /// </summary>
    /// <param name="force">Whether or not to force a full rebuild of the mesh data</param>
    /// <returns>True if an initialization occurred, false if it was skipped</returns>
    protected bool Initialize()
    {
        m_MaxTrailPoints = Mathf.Max(m_MaxTrailPoints, 3);
        // If we have a point mismatch, we force this operation
        if (m_Points != null && m_MaxTrailPoints == m_Points.Length)
        {
            return(false);
        }

        m_Points     = new Vector3[m_MaxTrailPoints];
        m_PointTimes = new float[m_MaxTrailPoints];
        Clear();

        if (m_Colors == null || m_Colors.Length == 0)
        {
            m_Colors    = new Color[1];
            m_Colors[0] = Color.white;
        }

        // For a trail renderer we assume one big chain
        // We need a control point for each billboard and a control point for each pipe connecting them together
        // We make this a circular trail so the update logic is easier.  This gives us (position * 2)
        var neededPoints = Mathf.Max((m_MaxTrailPoints * 2), 0);

        if (m_MeshData == null)
        {
            m_MeshData = new VRLineRendererInternal.MeshChain();
        }

        if (m_MeshData.reservedElements != neededPoints)
        {
            m_MeshData.worldSpaceData = true;
            m_MeshData.GenerateMesh(gameObject, true, neededPoints);

            if (neededPoints == 0)
            {
                return(true);
            }

            var pointCounter   = 0;
            var elementCounter = 0;
            var zeroVec        = Vector3.zero;
            var zeroColor      = new Color(0, 0, 0, 0);

            // Initialize everything to 0 so we don't render any trails at first
            m_MeshData.SetElementColor(0, ref zeroColor);
            while (pointCounter < m_Points.Length)
            {
                // Start point
                m_MeshData.SetElementSize(elementCounter, 0);
                m_MeshData.SetElementPosition(elementCounter, ref zeroVec);
                elementCounter++;

                // Pipe to the next point
                m_MeshData.SetElementSize(elementCounter, 0);
                m_MeshData.SetElementPipe(elementCounter, ref zeroVec, ref zeroVec);

                // Go onto the next point while retaining previous values we might need to lerp between
                elementCounter++;
                pointCounter++;
            }

            // Dirty all the MeshChain flags so everything gets refreshed
            m_MeshRenderer.enabled = false;
            m_MeshData.SetMeshDataDirty(VRLineRendererInternal.MeshChain.MeshRefreshFlag.All);
            m_MeshNeedsRefreshing = true;
        }
        return(true);
    }