Ejemplo n.º 1
0
        public override void Read(ResourceDataReader reader, params object[] parameters)
        {
            AABBMin         = reader.ReadVector4();
            AABBMax         = reader.ReadVector4();
            CellAABB        = reader.ReadStruct <NavMeshAABB>();
            DataPointer     = reader.ReadUInt64();
            SubTree1Pointer = reader.ReadUInt64();
            SubTree2Pointer = reader.ReadUInt64();
            SubTree3Pointer = reader.ReadUInt64();
            SubTree4Pointer = reader.ReadUInt64();
            Unused_54h      = reader.ReadUInt32();
            Unused_58h      = reader.ReadUInt32();
            Unused_5Ch      = reader.ReadUInt32();

            Data     = reader.ReadBlockAt <NavMeshSectorData>(DataPointer);
            SubTree1 = reader.ReadBlockAt <NavMeshSector>(SubTree1Pointer);
            SubTree2 = reader.ReadBlockAt <NavMeshSector>(SubTree2Pointer);
            SubTree3 = reader.ReadBlockAt <NavMeshSector>(SubTree3Pointer);
            SubTree4 = reader.ReadBlockAt <NavMeshSector>(SubTree4Pointer);
        }
Ejemplo n.º 2
0
        private void BuildStructs()
        {
            Vector3 posoffset   = Nav.SectorTree?.AABBMin.XYZ() ?? Vector3.Zero;
            Vector3 aabbsize    = Nav.AABBSize;
            Vector3 aabbsizeinv = 1.0f / aabbsize;

            var vertlist = new List <NavMeshVertex>();

            if (Vertices != null)
            {
                for (int i = 0; i < Vertices.Count; i++)
                {
                    vertlist.Add(NavMeshVertex.Create((Vertices[i] - posoffset) * aabbsizeinv));
                }
            }
            var polylist = new List <NavMeshPoly>();

            if (Polys != null)
            {
                for (int i = 0; i < Polys.Count; i++)
                {
                    Polys[i].Index = i;
                    polylist.Add(Polys[i].RawData);
                }
            }
            var portallist = new List <NavMeshPortal>();

            if (Portals != null)
            {
                for (int i = 0; i < Portals.Count; i++)
                {
                    var portal = Portals[i];
                    var pdata  = portal.RawData;
                    pdata.PositionFrom = NavMeshVertex.Create((portal.PositionFrom - posoffset) * aabbsizeinv);
                    pdata.PositionTo   = NavMeshVertex.Create((portal.PositionTo - posoffset) * aabbsizeinv);
                    portallist.Add(pdata);
                }
            }

            if (Points != null)
            {
                for (int i = 0; i < Points.Count; i++)
                {
                    var point = Points[i];
                    var pdata = point.RawData;
                    pdata.Position = point.Position;
                }
            }


            if (Nav.Vertices == null)
            {
                Nav.Vertices     = new NavMeshList <NavMeshVertex>();
                Nav.Vertices.VFT = 1080158456;
            }
            if (Nav.Indices == null)
            {
                Nav.Indices     = new NavMeshList <ushort>();
                Nav.Indices.VFT = 1080158424;
            }
            if (Nav.AdjPolys == null)
            {
                Nav.AdjPolys     = new NavMeshList <NavMeshAdjPoly>();
                Nav.AdjPolys.VFT = 1080158440;
            }
            if (Nav.Polys == null)
            {
                Nav.Polys     = new NavMeshList <NavMeshPoly>();
                Nav.Polys.VFT = 1080158408;
            }


            Nav.Vertices.RebuildList(vertlist);

            Nav.Indices.RebuildList(Indices);

            Nav.AdjPolys.RebuildList(AdjPolys);

            Nav.Polys.RebuildList(polylist);

            Nav.Portals      = (portallist.Count > 0) ? portallist.ToArray() : null;
            Nav.PortalsCount = (uint)(Nav.Portals?.Length ?? 0);
            //TODO: update portal links data.....


            for (int i = 0; i < Nav.Polys.ListParts.Count; i++) //reassign part id's on all the polys...
            {
                var listpart  = Nav.Polys.ListParts[i];
                var partitems = listpart?.Items;
                if (partitems == null)
                {
                    continue;
                }
                ushort iu = (ushort)i;
                for (int j = 0; j < partitems.Length; j++)
                {
                    partitems[j].PartID = iu;
                }
            }



            //Build Sector Tree
            int depth = 0;

            if ((Nav.ContentFlags & NavMeshFlags.Vehicle) == 0)
            {
                depth = 2;
            }
            //vehicle navmesh has a single level, static has 3..

            NavMeshSector orig = Nav.SectorTree;
            NavMeshSector root = new NavMeshSector();

            root.SetAABBs(orig.AABBMin.XYZ(), orig.AABBMax.XYZ());

            uint pointindex = 0;

            BuildSectorTree(root, depth, ref pointindex);

            Nav.SectorTree = root;
        }
Ejemplo n.º 3
0
        private void BuildSectorTree(NavMeshSector node, int depth, ref uint pointindex)
        {
            Vector3 min = node.AABBMin.XYZ();
            Vector3 max = node.AABBMax.XYZ();
            Vector3 cen = (min + max) * 0.5f;

            if (depth <= 0)
            {
                //go through polys and points and create new lists for this node
                NavMeshSectorData data = new NavMeshSectorData();
                node.Data = data;

                data.PointsStartID = pointindex;

                if (Polys != null)
                {
                    List <ushort> polyids = new List <ushort>();
                    for (int i = 0; i < Polys.Count; i++)
                    {
                        var poly = Polys[i];
                        var b    = poly._RawData.CellAABB;
                        if (BoxOverlaps(b, node.CellAABB))
                        {
                            polyids.Add((ushort)poly.Index);
                        }
                    }
                    if (polyids.Count > 0)
                    {
                        data.PolyIDs = polyids.ToArray();
                    }
                }

                if (Points != null)
                {
                    List <NavMeshPoint> points = new List <NavMeshPoint>();
                    for (int i = 0; i < Points.Count; i++)
                    {
                        var point = Points[i];
                        if (IsInBox(point.Position, min, max))
                        {
                            points.Add(point.RawData);
                        }
                    }
                    if (points.Count > 0)
                    {
                        data.Points = points.ToArray();
                        pointindex += (uint)points.Count;
                    }
                }
            }
            else
            {
                //recurse quadtree... clockwise from +XY (top right)
                int cdepth = depth - 1;
                node.SubTree1 = new NavMeshSector();
                node.SubTree2 = new NavMeshSector();
                node.SubTree3 = new NavMeshSector();
                node.SubTree4 = new NavMeshSector();
                node.SubTree1.SetAABBs(new Vector3(cen.X, cen.Y, cen.Z), new Vector3(max.X, max.Y, max.Z)); //for some reason Z values seem to get arranged like this...
                node.SubTree2.SetAABBs(new Vector3(cen.X, min.Y, 0.0f), new Vector3(max.X, cen.Y, 0.0f));
                node.SubTree3.SetAABBs(new Vector3(min.X, min.Y, min.Z), new Vector3(cen.X, cen.Y, cen.Z));
                node.SubTree4.SetAABBs(new Vector3(min.X, cen.Y, 0.0f), new Vector3(cen.X, max.Y, 0.0f));
                BuildSectorTree(node.SubTree1, cdepth, ref pointindex);
                BuildSectorTree(node.SubTree2, cdepth, ref pointindex);
                BuildSectorTree(node.SubTree3, cdepth, ref pointindex);
                BuildSectorTree(node.SubTree4, cdepth, ref pointindex);
            }
        }
Ejemplo n.º 4
0
        private void BuildStructs()
        {
            Vector3 posoffset   = Nav.SectorTree?.AABBMin.XYZ() ?? Vector3.Zero;
            Vector3 aabbsize    = Nav.AABBSize;
            Vector3 aabbsizeinv = 1.0f / aabbsize;

            var vertlist    = new List <NavMeshVertex>();
            var indslist    = new List <ushort>();
            var edgelist    = new List <NavMeshEdge>();
            var polylist    = new List <NavMeshPoly>();
            var portallist  = new List <NavMeshPortal>();
            var portallinks = new List <ushort>();

            var vertdict = new Dictionary <Vector3, ushort>();
            var areadict = new Dictionary <uint, uint>();
            var arealist = new List <uint>();
            var areaid   = Nav.AreaID;

            EnsureEdgeAreaID(areaid, areadict, arealist);
            EnsureEdgeAreaID(0x3FFF, areadict, arealist);
            EnsureEdgeAreaID(areaid - 100, areadict, arealist);
            EnsureEdgeAreaID(areaid - 1, areadict, arealist);
            EnsureEdgeAreaID(areaid + 1, areadict, arealist);
            EnsureEdgeAreaID(areaid + 100, areadict, arealist);



            if (Polys != null) //rebuild vertices, indices, edges and polys lists from poly data.
            {
                for (int i = 0; i < Polys.Count; i++)
                {
                    var poly = Polys[i];
                    var vc   = poly.Vertices?.Length ?? 0;
                    //poly.AreaID = (ushort)Nav.AreaID;
                    poly._RawData.IndexID = (ushort)indslist.Count;
                    for (int n = 0; n < vc; n++)
                    {
                        Vector3 v = poly.Vertices[n];
                        YnvEdge e = ((poly.Edges != null) && (n < poly.Edges.Length)) ? poly.Edges[n] : null;
                        ushort  ind;
                        if (!vertdict.TryGetValue(v, out ind))
                        {
                            ind         = (ushort)vertlist.Count;
                            vertdict[v] = ind;
                            vertlist.Add(NavMeshVertex.Create(Vector3.Clamp((v - posoffset) * aabbsizeinv, Vector3.Zero, Vector3.One)));
                        }
                        if ((poly.Indices != null) && (n < poly.Indices.Length))
                        {
                            poly.Indices[n] = ind;
                        }
                        indslist.Add(ind);

                        NavMeshEdge edge;
                        if (e != null)
                        {
                            if (e.Poly1 != null)
                            {
                                e.PolyID1 = (uint)e.Poly1.Index;
                                e.AreaID1 = e.Poly1.AreaID;
                                if (e.AreaID1 == 0x3FFF)
                                {
                                }  //debug
                            }
                            if (e.Poly2 != null)
                            {
                                e.PolyID2 = (uint)e.Poly2.Index;
                                e.AreaID2 = e.Poly2.AreaID;
                                if (e.AreaID2 == 0x3FFF)
                                {
                                }  //debug
                            }
                            if ((e.AreaID1 == 0) || (e.AreaID2 == 0))
                            {
                            }  //debug
                            e._RawData._Poly1.AreaIDInd = EnsureEdgeAreaID(e.AreaID1, areadict, arealist);
                            e._RawData._Poly2.AreaIDInd = EnsureEdgeAreaID(e.AreaID2, areadict, arealist);
                            edge = e.RawData;
                        }
                        else
                        {
                            var areaind = EnsureEdgeAreaID(0x3FFF, areadict, arealist);
                            edge = new NavMeshEdge();//create an empty edge
                            edge._Poly1.PolyID    = 0x3FFF;
                            edge._Poly2.PolyID    = 0x3FFF;
                            edge._Poly1.AreaIDInd = areaind;
                            edge._Poly2.AreaIDInd = areaind;
                        }
                        edgelist.Add(edge);
                    }
                    poly._RawData.IndexCount      = vc;
                    poly._RawData.PortalLinkID    = (uint)portallinks.Count;//these shouldn't be directly editable!
                    poly._RawData.PortalLinkCount = (byte)(poly.PortalLinks?.Length ?? 0);
                    if (poly.PortalLinks != null)
                    {
                        portallinks.AddRange(poly.PortalLinks);
                    }
                    poly.Index = i;       //this should be redundant...
                    poly.CalculateAABB(); //make sure this is up to date!
                    polylist.Add(poly.RawData);
                }
            }

            if (Portals != null)
            {
                for (int i = 0; i < Portals.Count; i++)
                {
                    var portal = Portals[i];
                    var pdata  = portal.RawData;
                    pdata.PositionFrom = NavMeshVertex.Create((portal.PositionFrom - posoffset) * aabbsizeinv);
                    pdata.PositionTo   = NavMeshVertex.Create((portal.PositionTo - posoffset) * aabbsizeinv);
                    portallist.Add(pdata);
                }
            }

            if (Points != null) //points will be built into the sector tree
            {
                for (int i = 0; i < Points.Count; i++)
                {
                    var point = Points[i];
                    var pdata = point.RawData;
                    pdata.Position = point.Position;
                }
            }


            if (Nav.Vertices == null)
            {
                Nav.Vertices     = new NavMeshList <NavMeshVertex>();
                Nav.Vertices.VFT = 1080158456;
            }
            if (Nav.Indices == null)
            {
                Nav.Indices     = new NavMeshList <ushort>();
                Nav.Indices.VFT = 1080158424;
            }
            if (Nav.Edges == null)
            {
                Nav.Edges     = new NavMeshList <NavMeshEdge>();
                Nav.Edges.VFT = 1080158440;
            }
            if (Nav.Polys == null)
            {
                Nav.Polys     = new NavMeshList <NavMeshPoly>();
                Nav.Polys.VFT = 1080158408;
            }


            Nav.Vertices.RebuildList(vertlist);
            Nav.VerticesCount = Nav.Vertices.ItemCount;

            Nav.Indices.RebuildList(indslist);

            Nav.Edges.RebuildList(edgelist);
            Nav.EdgesIndicesCount = Nav.Indices.ItemCount;

            Nav.Polys.RebuildList(polylist);
            Nav.PolysCount = Nav.Polys.ItemCount;

            Nav.Portals          = (portallist.Count > 0) ? portallist.ToArray() : null;
            Nav.PortalsCount     = (uint)(Nav.Portals?.Length ?? 0);
            Nav.PortalLinks      = (portallinks.Count > 0) ? portallinks.ToArray() : null;
            Nav.PortalLinksCount = (uint)(Nav.PortalLinks?.Length ?? 0);

            var adjAreaIds = new NavMeshUintArray();

            adjAreaIds.Set(arealist.ToArray());
            Nav.AdjAreaIDs = adjAreaIds;


            for (int i = 0; i < Nav.Polys.ListParts.Count; i++) //reassign part id's on all the polys...
            {
                var listpart  = Nav.Polys.ListParts[i];
                var partitems = listpart?.Items;
                if (partitems == null)
                {
                    continue;
                }
                ushort iu = (ushort)i;
                for (int j = 0; j < partitems.Length; j++)
                {
                    partitems[j].PartID = iu;
                }
            }



            //Build Sector Tree
            int depth = 0;

            if ((Nav.ContentFlags & NavMeshFlags.Vehicle) == 0)
            {
                depth = 2;
            }
            //vehicle navmesh has a single level, static has 3..

            NavMeshSector orig = Nav.SectorTree;
            NavMeshSector root = new NavMeshSector();

            root.SetAABBs(orig.AABBMin.XYZ(), orig.AABBMax.XYZ());

            uint pointindex = 0;

            BuildSectorTree(root, depth, ref pointindex);

            Nav.SectorTree = root;
        }