Example #1
0
        private IEnumerator EnableLastRendererCoRoutine()
        {
            LineRendererMesh lineRenderer = activeLineRenderers[activeLineRenderers.Count - 1];
            int tag = ++lineRenderer.Tag; // in case it gets cleaned up for later

            yield return(new WaitForSecondsLightning(MinimumDelay));

            EnableLineRenderer(lineRenderer, tag);
        }
Example #2
0
        private void EnableLineRenderer(LineRendererMesh lineRenderer, int tag)
        {
            bool shouldPopulate = (lineRenderer != null && lineRenderer.GameObject != null && lineRenderer.Tag == tag && IsActive);

            if (shouldPopulate)
            {
                lineRenderer.PopulateMesh();
            }
        }
Example #3
0
        private LineRendererMesh GetOrCreateLineRenderer()
        {
            LineRendererMesh lineRenderer;

            while (true)
            {
                if (lineRendererCache.Count == 0)
                {
                    lineRenderer = new LineRendererMesh();
                }
                else
                {
                    int index = lineRendererCache.Count - 1;
                    lineRenderer = lineRendererCache[index];
                    lineRendererCache.RemoveAt(index);
                    if (lineRenderer == null || lineRenderer.Transform == null)
                    {
                        // destroyed by some other means, try again for cache...
                        continue;
                    }
                }
                break;
            }

            // clear parent - this ensures that the rotation and scale can be reset before assigning a new parent
            lineRenderer.Transform.parent     = null;
            lineRenderer.Transform.rotation   = Quaternion.identity;
            lineRenderer.Transform.localScale = Vector3.one;
            lineRenderer.Transform.parent     = dependencies.Parent.transform;
            lineRenderer.GameObject.layer     = dependencies.Parent.layer; // maintain the layer of the parent

            if (dependencies.UseWorldSpace)
            {
                lineRenderer.GameObject.transform.position = Vector3.zero;
            }
            else
            {
                lineRenderer.GameObject.transform.localPosition = Vector3.zero;
            }

            lineRenderer.Material = (HasGlow ? dependencies.LightningMaterialMesh : dependencies.LightningMaterialMeshNoGlow);
            if (!string.IsNullOrEmpty(dependencies.SortLayerName))
            {
                lineRenderer.MeshRenderer.sortingLayerName = dependencies.SortLayerName;
                lineRenderer.MeshRenderer.sortingOrder     = dependencies.SortOrderInLayer;
            }
            else
            {
                lineRenderer.MeshRenderer.sortingLayerName = null;
                lineRenderer.MeshRenderer.sortingOrder     = 0;
            }

            activeLineRenderers.Add(lineRenderer);

            return(lineRenderer);
        }
Example #4
0
        private Transform RenderLightningBolt(LightningBoltQualitySetting quality, int generations, int startGroupIndex, int endGroupIndex, LightningBoltParameters parameters)
        {
            if (segmentGroups.Count == 0 || startGroupIndex >= segmentGroups.Count || endGroupIndex > segmentGroups.Count)
            {
                return(null);
            }

            Transform transform         = null;
            LightningLightParameters lp = parameters.LightParameters;

            if (lp != null)
            {
                if ((hasLight |= lp.HasLight))
                {
                    lp.LightPercent       = Mathf.Clamp(lp.LightPercent, Mathf.Epsilon, 1.0f);
                    lp.LightShadowPercent = Mathf.Clamp(lp.LightShadowPercent, 0.0f, 1.0f);
                }
                else
                {
                    lp = null;
                }
            }

            LightningBoltSegmentGroup mainTrunkGroup = segmentGroups[startGroupIndex];
            Vector3 start = mainTrunkGroup.Segments[mainTrunkGroup.StartIndex].Start;
            Vector3 end   = mainTrunkGroup.Segments[mainTrunkGroup.StartIndex + mainTrunkGroup.SegmentCount - 1].End;

            parameters.FadePercent = Mathf.Clamp(parameters.FadePercent, 0.0f, 0.5f);

            // create a new line renderer mesh right now if we have a custom transform
            if (parameters.CustomTransform != null)
            {
                LineRendererMesh currentLineRenderer = (activeLineRenderers.Count == 0 || !activeLineRenderers[activeLineRenderers.Count - 1].Empty ? null : activeLineRenderers[activeLineRenderers.Count - 1]);

                if (currentLineRenderer == null)
                {
#if !UNITY_WEBGL
                    if (dependencies.ThreadState != null)
                    {
                        // we need to block until this action is run, Unity objects can only be modified and created on the main thread
                        dependencies.ThreadState.AddActionForMainThread(() =>
                        {
                            EnableCurrentLineRenderer();
                            currentLineRenderer = GetOrCreateLineRenderer();
                        }, true);
                    }
                    else
#endif

                    {
                        EnableCurrentLineRenderer();
                        currentLineRenderer = GetOrCreateLineRenderer();
                    }
                }
                if (currentLineRenderer == null)
                {
                    return(null);
                }

                currentLineRenderer.CustomTransform = parameters.CustomTransform;
                transform = currentLineRenderer.Transform;
            }

            for (int i = startGroupIndex; i < endGroupIndex; i++)
            {
                LightningBoltSegmentGroup group = segmentGroups[i];
                group.Delay     = parameters.delaySeconds;
                group.LifeTime  = parameters.LifeTime;
                group.PeakStart = group.LifeTime * parameters.FadePercent;
                group.PeakEnd   = group.LifeTime - group.PeakStart;
                float peakGap = group.PeakEnd - group.PeakStart;
                float fadeOut = group.LifeTime - group.PeakEnd;
                group.PeakStart      *= parameters.FadeInMultiplier;
                group.PeakEnd         = group.PeakStart + (peakGap * parameters.FadeFullyLitMultiplier);
                group.LifeTime        = group.PeakEnd + (fadeOut * parameters.FadeOutMultiplier);
                group.LightParameters = lp;
                RenderGroup(group, parameters);
            }

#if !UNITY_WEBGL
            if (dependencies.ThreadState != null)
            {
                dependencies.ThreadState.AddActionForMainThread(() =>
                {
                    RenderParticleSystems(start, end, parameters.TrunkWidth, parameters.LifeTime, parameters.delaySeconds);

                    // create lights only on the main trunk
                    if (lp != null)
                    {
                        CreateLightsForGroup(segmentGroups[startGroupIndex], lp, quality, parameters.maxLights);
                    }
                });
            }
            else
#endif

            {
                RenderParticleSystems(start, end, parameters.TrunkWidth, parameters.LifeTime, parameters.delaySeconds);

                // create lights only on the main trunk
                if (lp != null)
                {
                    CreateLightsForGroup(segmentGroups[startGroupIndex], lp, quality, parameters.maxLights);
                }
            }

            return(transform);
        }
Example #5
0
        private void RenderGroup(LightningBoltSegmentGroup group, LightningBoltParameters p)
        {
            if (group.SegmentCount == 0)
            {
                return;
            }

#if UNITY_WEBGL
            float timeOffset = 0.0f;
#else
            float timeOffset = (dependencies.ThreadState == null ? 0.0f : (float)(DateTime.UtcNow - startTimeOffset).TotalSeconds);
#endif

            float   timeStart    = timeSinceLevelLoad + group.Delay + timeOffset;
            Vector4 fadeLifeTime = new Vector4(timeStart, timeStart + group.PeakStart, timeStart + group.PeakEnd, timeStart + group.LifeTime);
            float   radius       = group.LineWidth * 0.5f * LightningBoltParameters.Scale;
            int     lineCount    = (group.Segments.Count - group.StartIndex);
            float   radiusStep   = (radius - (radius * group.EndWidthMultiplier)) / (float)lineCount;

            // growth multiplier
            float timeStep;
            if (p.GrowthMultiplier > 0.0f)
            {
                timeStep   = (group.LifeTime / (float)lineCount) * p.GrowthMultiplier;
                timeOffset = 0.0f;
            }
            else
            {
                timeStep   = 0.0f;
                timeOffset = 0.0f;
            }

            LineRendererMesh currentLineRenderer = (activeLineRenderers.Count == 0 ? GetOrCreateLineRenderer() : activeLineRenderers[activeLineRenderers.Count - 1]);

            // if we have filled up the mesh, we need to start a new line renderer
            if (!currentLineRenderer.PrepareForLines(lineCount))
            {
                if (currentLineRenderer.CustomTransform != null)
                {
                    // can't create multiple meshes if using a custom transform callback
                    return;
                }

#if !UNITY_WEBGL
                if (dependencies.ThreadState != null)
                {
                    // we need to block until this action is run, Unity objects can only be modified and created on the main thread
                    dependencies.ThreadState.AddActionForMainThread(() =>
                    {
                        EnableCurrentLineRenderer();
                        currentLineRenderer = GetOrCreateLineRenderer();
                    }, true);
                }
                else
#endif

                {
                    EnableCurrentLineRenderer();
                    currentLineRenderer = GetOrCreateLineRenderer();
                }
            }

            currentLineRenderer.BeginLine(group.Segments[group.StartIndex].Start, group.Segments[group.StartIndex].End, radius, group.Color, p.Intensity, fadeLifeTime, p.GlowWidthMultiplier, p.GlowIntensity);
            for (int i = group.StartIndex + 1; i < group.Segments.Count; i++)
            {
                radius -= radiusStep;
                if (p.GrowthMultiplier < 1.0f)
                {
                    timeOffset  += timeStep;
                    fadeLifeTime = new Vector4(timeStart + timeOffset, timeStart + group.PeakStart + timeOffset, timeStart + group.PeakEnd, timeStart + group.LifeTime);
                }
                currentLineRenderer.AppendLine(group.Segments[i].Start, group.Segments[i].End, radius, group.Color, p.Intensity, fadeLifeTime, p.GlowWidthMultiplier, p.GlowIntensity);
            }
        }
Example #6
0
 public void End(LightningBolt lightningBolt)
 {
     if (currentLineRenderer != null)
     {
         Script.StartCoroutine(EnableRenderer(currentLineRenderer, lightningBolt));
         currentLineRenderer = null;
     }
 }
Example #7
0
        private LineRendererMesh CreateLineRenderer(LightningBolt lightningBolt, List<LineRendererMesh> lineRenderers)
        {
            LineRendererMesh lineRenderer;

            if (rendererCache.Count == 0)
            {
                // create a line renderer in a new game object underneath the parent
                GameObject obj = new GameObject();
                obj.name = "LightningBoltMeshRenderer";
                obj.hideFlags = HideFlags.HideAndDontSave;
                lineRenderer = obj.AddComponent<LineRendererMesh>();
            }
            else
            {
                lineRenderer = rendererCache[rendererCache.Count - 1];
                rendererCache.RemoveAt(rendererCache.Count - 1);
            }

            // clear parent - this ensures that the rotation and scale can be reset before assigning a new parent
            lineRenderer.gameObject.transform.parent = null;
            lineRenderer.gameObject.transform.rotation = Quaternion.identity;
            lineRenderer.gameObject.transform.localScale = Vector3.one;
            lineRenderer.gameObject.transform.parent = lightningBolt.Parent.transform;
            lineRenderer.gameObject.layer = lightningBolt.Parent.layer; // maintain the layer of the parent

            if (lightningBolt.UseWorldSpace)
            {
                lineRenderer.gameObject.transform.position = Vector3.zero;
            }
            else
            {
                lineRenderer.gameObject.transform.localPosition = Vector3.zero;
            }

            lineRenderer.Material = (lightningBolt.HasGlow ? Material : MaterialNoGlow);
            lineRenderer.MeshRenderer.sortingLayerName = lightningBolt.SortLayerName;
            lineRenderer.MeshRenderer.sortingOrder = lightningBolt.SortOrderInLayer;
            currentLineRenderer = lineRenderer;
            lineRenderers.Add(lineRenderer);

            return lineRenderer;
        }
Example #8
0
        private IEnumerator EnableRenderer(LineRendererMesh renderer, LightningBolt lightningBolt)
        {
            yield return new WaitForSeconds(lightningBolt.MinimumDelay);

            if (renderer != null && lightningBolt.IsActive)
            {
                renderer.Begin();
            }
        }