コード例 #1
0
        void RemoveTimeOutPoints()
        {
            List <CatmullRomPoint> toRemoveList = new List <CatmullRomPoint>();

            for (var i = 0; i < catmullRomPointList.Count; i++)
            {
                CatmullRomPoint point = catmullRomPointList[i];
                if (Time.realtimeSinceStartup - point.createTime > life_time)
                {
                    toRemoveList.Add(point);
                }
            }

            for (var i = 0; i < toRemoveList.Count; i++)
            {
                CatmullRomPoint point = toRemoveList[i];
                catmullRomPointList.Remove(point);
            }
        }
コード例 #2
0
        public CatmullRomSegment(CatmullRomPoint p0, CatmullRomPoint p1, CatmullRomPoint p2, CatmullRomPoint p3,
                                 int subSegmentNum)
        {
            this.p0            = p0;
            this.p1            = p1;
            this.p2            = p2;
            this.p3            = p3;
            this.subSegmentNum = subSegmentNum;

            length = 0;
            for (float i = 0; i < subSegmentNum; i++)
            {
                var point0      = GetPoint(i / subSegmentNum);
                var tangent0    = GetTangent(i / subSegmentNum);
                var createTime0 = Mathf.Lerp(p2.createTime, p3.createTime, i / subSegmentNum);
                var point1      = GetPoint((i + 1) / subSegmentNum);
                var tangent1    = GetTangent((i + 1) / subSegmentNum);
                var createTime1 = Mathf.Lerp(p2.createTime, p3.createTime, (i + 1) / subSegmentNum);
                var segment     = new Segment(new Knot(point0, tangent0, createTime0), new Knot(point1, tangent1, createTime1));
                subSegmentList.Add(segment);
                length += segment.length;
            }
        }
コード例 #3
0
        public CatmullRomSpline(CatmullRomPoint[] orgPoints, int subSegmentNum)
        {
            segment_num = orgPoints.Length - 1;
            //添加头尾顺延曲线方向的两个点
            var list  = new List <CatmullRomPoint>(orgPoints);
            var first = new CatmullRomPoint(2 * orgPoints[0].position - orgPoints[1].position,
                                            orgPoints[0].createTime);
            var last = new CatmullRomPoint(
                2 * orgPoints[orgPoints.Length - 1].position - orgPoints[orgPoints.Length - 2].position,
                orgPoints[orgPoints.Length - 1].createTime);

            list.Insert(0, first);
            list.Add(last);
            this.orgPoints = list.ToArray();

            length = 0;
            for (var i = 1; i <= this.orgPoints.Length - 3; i++)
            {
                segmentList.Add(new CatmullRomSegment(this.orgPoints[i - 1], this.orgPoints[i], this.orgPoints[i + 1],
                                                      this.orgPoints[i + 2], subSegmentNum));
                length += segmentList[segmentList.Count - 1].length;
            }
        }
コード例 #4
0
        void Update()
        {
            Vector3 currentPoint = this.transform.position;


            bool isNeedAddPoint = false;

            if (catmullRomPointList.Count < 2)
            {
                isNeedAddPoint = true;
            }
            else
            {
                float vertexDistance =
                    (currentPoint - catmullRomPointList[catmullRomPointList.Count - 2].position).magnitude;
                if (vertexDistance > emissionDistance)
                {
                    isNeedAddPoint = true;
                }
            }


            if (isNeedAddPoint)
            {
                catmullRomPoint = new CatmullRomPoint(currentPoint, Time.realtimeSinceStartup);
                catmullRomPointList.Add(catmullRomPoint);
            }
            else
            {
                catmullRomPoint            = catmullRomPointList[catmullRomPointList.Count - 1];
                catmullRomPoint.position   = currentPoint;
                catmullRomPoint.createTime = Time.realtimeSinceStartup;
            }


            RemoveTimeOutPoints();
            if (catmullRomPointList.Count < 2)
            {
                catmullRomMesh.Clear();
                return;
            }

            CatmullRomPoint[] catmullRomPoints = catmullRomPointList.ToArray();
            catmullRomPoints.Reverse();

            spline = new CatmullRomSpline(catmullRomPoints, subdivision);

            newVerticeList.Clear();
            newUVList.Clear();
            newTriangleList.Clear();


            //float splineLength = Mathf.Max(0, spline.GetLength()-0.1f);
            float splineLength = Mathf.Max(0, spline.length);

            int  n = 0;
            bool isAngleDiffBig = false;             //用于合并,当角度相差太大的时候,不进行合并

            float eachAddDistance = 0.25f * width;

            //float eachAddDistance = 0.001f * width;
            for (float distance = 0;
                 distance <= splineLength;
                 distance = distance + eachAddDistance > splineLength ? splineLength : distance + eachAddDistance)
            {
                curPoint   = spline.GetPointAtDistance(distance);
                curTangent = spline.GetTangentAtDistance(distance);

                Vector3 biNormal = CatmullRomSpline.ComputeBinormal(curTangent.position, normal);

                float timeSpan   = Time.realtimeSinceStartup - curPoint.createTime;
                float lerpHeight = height;


                //合并相邻两个切线率相差不多的segment
                //            if (n > 1)
                //            {
                //                float lastDistance = distance - width;
                //                lastTangent = spline.GetTangentAtDistance(lastDistance);
                //                float angle = Vector3.Angle(lastTangent.position, curTangent.position);
                //                if (angle <= 0.5f)
                //                {
                //                    if (!isAngleDiffBig)
                //                    {
                //                        for (int i = 0; i < 2; i++)
                //                        {
                //                            newVerticeList.RemoveLast();
                //                            newUVList.RemoveLast();
                //                        }
                //                        for (int i = 0; i < 6; i++)
                //                            newTriangleList.RemoveLast();
                //                        n--;
                //                    }
                //                    else
                //                        isAngleDiffBig = false;
                //                }
                //                else
                //                {
                //                    isAngleDiffBig = true;
                //                }
                //            }

                //需要添加epsilonAdd细小的offset,才能显示在mobile手机上,手机上刚好的在摄像机的nearClipPlane上是显示不出来的
                Vector3 epsilonAdd = camera.transform.forward * epsilon;

                newVerticeList.Add(curPoint.position - (biNormal * (lerpHeight * 0.5f)) + epsilonAdd);
                newVerticeList.Add(curPoint.position + (biNormal * (lerpHeight * 0.5f)) + epsilonAdd);


                float lerp = 0;
                if (splineLength < width)                 //少于width的用正常lerp
                {
                    lerp = distance / splineLength;
                }
                else                              //大于width的时候特殊处理
                {
                    if (distance <= 0.5f * width) //少于0.5f * width的部分占全图片的50%
                    {
                        lerp = 0.5f * (distance / (0.5f * width));
                    }
                    else                     //线段的其他部分平分剩下图片的50%
                    {
                        lerp = 0.5f + 0.5f * ((distance - 0.5f * width) / (splineLength - 0.5f * width));
                    }
                }


                newUVList.Add(new Vector2(lerp, 0));
                newUVList.Add(new Vector2(lerp, 1));

                if (n > 0)
                {
                    newTriangleList.Add((n * 2) - 2);
                    newTriangleList.Add((n * 2) - 1);
                    newTriangleList.Add(n * 2);

                    newTriangleList.Add((n * 2) + 1);
                    newTriangleList.Add(n * 2);
                    newTriangleList.Add((n * 2) - 1);
                }

                if (distance >= splineLength - dd)
                {
                    break;
                }

                if (distance == splineLength)
                {
                    break;
                }

                n++;
            }

            catmullRomMesh.Clear();
            catmullRomMesh.vertices  = newVerticeList.ToArray();
            catmullRomMesh.uv        = newUVList.ToArray();
            catmullRomMesh.triangles = newTriangleList.ToArray();
        }