Пример #1
0
 public WalkCell(Poll topLeft, Poll topRight, Poll bottomRight, Poll bottomLeft, float pollSpacing, float playerHeight, float playerStepHeight, List <MathUtils.Cylinder> cylinders = null)
 {
     FillWalkPoints(topLeft, topRight, bottomRight, bottomLeft, pollSpacing, playerHeight, playerStepHeight, cylinders);
 }
Пример #2
0
        void FillWalkPoints(Poll topLeft, Poll topRight, Poll bottomRight, Poll bottomLeft, float pollSpacing, float playerHeight, float playerStepHeight, List <MathUtils.Cylinder> cylinders)
        {
            List <Vector3> points = new List <Vector3>(8);

            List <float> tLeft  = new List <float>(topLeft.yHeights);
            List <float> tRight = new List <float>(topRight.yHeights);
            List <float> bRight = new List <float>(bottomRight.yHeights);
            List <float> bLeft  = new List <float>(bottomLeft.yHeights);

            short configuration = 0;
            float height        = 0;
            short retConfig     = 0;
            float retHeight     = 0;
            short ConfigCount   = 1;

            foreach (float p in tLeft)
            {
                points.Clear();
                configuration = 0;
                height        = 0;
                retConfig     = 0;
                retHeight     = 0;
                ConfigCount   = 1;


                points.Add(topLeft.postition + Vector3.up * p);
                configuration += 8;// 8 = top left
                height         = p;

                // 4 = top right
                (retConfig, retHeight) = HasPointInWalkGroup(ref tRight, topRight.postition, ref points, p, 4, playerStepHeight);
                configuration         += retConfig;
                if (retConfig > 0)
                {
                    ConfigCount++;
                }
                height += retHeight;

                // 2 = bottom right
                (retConfig, retHeight) = HasPointInWalkGroup(ref bRight, bottomRight.postition, ref points, p, 2, playerStepHeight);
                configuration         += retConfig;
                if (retConfig > 0)
                {
                    ConfigCount++;
                }
                height += retHeight;

                // 1 = bottom left
                (retConfig, retHeight) = HasPointInWalkGroup(ref bLeft, bottomLeft.postition, ref points, p, 1, playerStepHeight);
                configuration         += retConfig;
                if (retConfig > 0)
                {
                    ConfigCount++;
                }
                height += retHeight;


                height /= ConfigCount;

                if ((configuration & 4) != 4)
                {
                    (retConfig, retHeight) = HasPointInWalkGroup(ref tRight, topRight.postition, ref points, height, 4, playerStepHeight);
                    configuration         += retConfig;
                    if (retConfig > 0)
                    {
                        ConfigCount++;
                    }
                    height += retHeight;
                }

                if ((configuration & 2) != 2)
                {
                    (retConfig, retHeight) = HasPointInWalkGroup(ref bRight, bottomRight.postition, ref points, height, 2, playerStepHeight);
                    configuration         += retConfig;
                    if (retConfig > 0)
                    {
                        ConfigCount++;
                    }
                    height += retHeight;
                }

                if ((configuration & 1) != 1)
                {
                    (retConfig, retHeight) = HasPointInWalkGroup(ref bLeft, bottomLeft.postition, ref points, height, 1, playerStepHeight);
                    configuration         += retConfig;
                    if (retConfig > 0)
                    {
                        ConfigCount++;
                    }
                    height += retHeight;
                }

                if (configuration != 15)
                {
                    configuration = Contains_A_BlockedWalkEdge(topLeft, topRight, bottomRight, bottomLeft, playerStepHeight, points, configuration);
                }
                if (points.Count > 2)
                {
                    points.Add(topLeft.postition + Vector3.up * p);
                }

                walkGroups.Add(new WalkPointGroup(points.ToArray(), configuration, pollSpacing, playerHeight, playerStepHeight, cylinders));
            }

            foreach (float p in tRight)
            {
                points.Clear();
                configuration = 0;
                height        = 0;
                retConfig     = 0;
                retHeight     = 0;
                ConfigCount   = 1;

                points.Add(topRight.postition + Vector3.up * p);
                configuration += 4;// 4 = top right

                // 2 = bottom right
                (retConfig, retHeight) = HasPointInWalkGroup(ref bRight, bottomRight.postition, ref points, p, 2, playerStepHeight);
                configuration         += retConfig;
                if (retConfig > 0)
                {
                    ConfigCount++;
                }
                height += retHeight;

                // 1 = bottom left
                (retConfig, retHeight) = HasPointInWalkGroup(ref bLeft, bottomLeft.postition, ref points, p, 1, playerStepHeight);
                configuration         += retConfig;
                if (retConfig > 0)
                {
                    ConfigCount++;
                }
                height += retHeight;

                configuration = Contains_A_BlockedWalkEdge(topLeft, topRight, bottomRight, bottomLeft, playerStepHeight, points, configuration);

                if (points.Count > 2)
                {
                    points.Add(topRight.postition + Vector3.up * p);
                }

                walkGroups.Add(new WalkPointGroup(points.ToArray(), configuration, pollSpacing, playerHeight, playerStepHeight, cylinders));
            }

            foreach (float p in bRight)
            {
                points.Clear();
                configuration = 0;
                height        = 0;
                retConfig     = 0;
                retHeight     = 0;
                ConfigCount   = 1;

                points.Add(bottomRight.postition + Vector3.up * p);
                configuration += 2;// 2 = bottom right

                // 1 = bottom left
                (retConfig, retHeight) = HasPointInWalkGroup(ref bLeft, bottomLeft.postition, ref points, p, 1, playerStepHeight);
                configuration         += retConfig;
                if (retConfig > 0)
                {
                    ConfigCount++;
                }
                height += retHeight;

                configuration = Contains_A_BlockedWalkEdge(topLeft, topRight, bottomRight, bottomLeft, playerStepHeight, points, configuration);

                if (points.Count > 2)
                {
                    points.Add(bottomRight.postition + Vector3.up * p);
                }

                walkGroups.Add(new WalkPointGroup(points.ToArray(), configuration, pollSpacing, playerHeight, playerStepHeight, cylinders));
            }

            foreach (float p in bLeft)
            {
                points.Clear();
                configuration = 0;

                points.Add(bottomLeft.postition + Vector3.up * p);
                configuration += 1;// 1 = bottom left

                configuration = Contains_A_BlockedWalkEdge(topLeft, topRight, bottomRight, bottomLeft, playerStepHeight, points, configuration);


                walkGroups.Add(new WalkPointGroup(points.ToArray(), configuration, pollSpacing, playerHeight, playerStepHeight, cylinders));
            }
        }
Пример #3
0
        private static short Contains_A_BlockedWalkEdge(Poll topLeft, Poll topRight, Poll bottomRight, Poll bottomLeft, float playerStepHeight, List <Vector3> points, short configuration)
        {
            for (int i = 0; i < points.Count && configuration > 0; i++)
            {
                Vector3 v = points[i];
                configuration = ContainsBlockedWalkPoint(topLeft, configuration, v);

                if (configuration < 0)
                {
                    break;
                }

                configuration = ContainsBlockedWalkPoint(topRight, configuration, v);

                if (configuration < 0)
                {
                    break;
                }

                configuration = ContainsBlockedWalkPoint(bottomRight, configuration, v);

                if (configuration < 0)
                {
                    break;
                }

                configuration = ContainsBlockedWalkPoint(bottomLeft, configuration, v);
            }

            return(configuration);
        }
Пример #4
0
        public void GenerateWalkGrid(float squareSize, int sideCount, float playerHeight, float stepHeight, float playerRadius, Vector3 pos)
        {
            if (squareSize <= 0.01 || sideCount < 1)
            {
                return;
            }

            pos.y = maxHeight;


            Poll[,] polls = new Poll[sideCount, sideCount];


            float spacing = (1f / (sideCount - 1)) * squareSize;

            for (int x = 0; x < sideCount; x++)
            {
                for (int y = 0; y < sideCount; y++)
                {
                    Vector3 point = pos + new Vector3(0 - (squareSize / 2) + x * spacing, 0, 0 - (squareSize / 2) + y * spacing);

                    RaycastHit[] hits = Physics.RaycastAll(point, Vector3.down);

                    hits = hits.OrderBy(v => v.point.y).Reverse().ToArray();

                    List <float> validPoints = new List <float>();

                    if (hits.Length != 0)
                    {
                        List <Collider> blockerCollider = new List <Collider>();

                        for (int h = 0; h < hits.Length; h++)
                        {
                            bool valid = true;

                            RaycastHit hit = hits[h];
                            RaycastHit hit2;

                            if (hit.collider.gameObject.layer == 8)
                            {
                                blockerCollider.Add(hit.collider);
                                valid = false;
                            }
                            else
                            {
                                foreach (var c in blockerCollider)
                                {
                                    if (IsPointInCollider(c, hit.point))
                                    {
                                        valid = false;
                                        break;
                                    }
                                }
                            }

                            if (valid && h != 0 &&
                                (hit.point.y + playerHeight > hits[h - 1].point.y || Physics.Raycast(hit.point, Vector3.up, out hit2, playerHeight)))
                            {
                                valid = false;
                            }

                            if (valid)
                            {
                                validPoints.Add(hit.point.y);
                            }

                            if (drawCross)
                            {
                                GL_Utils.DrawCrossNormal(hit.point + Vector3.up * 0.01f, hit.normal, valid ? Color.white : Color.red);
                            }
                        }


                        if (drawRay)
                        {
                            GL_Utils.DrawLine(point, hits[hits.Length - 1].point, Color.green);
                        }
                    }
                    polls[x, y] = new Poll(new Vector3(point.x, 0, point.z), validPoints);
                }
            }

            cellGrid = new CellGrid(polls, spacing, playerHeight, stepHeight, playerRadius);
        }