示例#1
0
        public static WavefrontObjFile ToObj(NiFile model)
        {
            var obj = new WavefrontObjFile();
            //var matrix = Matrix.RotationZ((float)Math.PI) * Matrix.RotationX(-(float)Math.PI/2f);
            float d90    = (float)Math.PI / 2f;
            var   matrix = Matrix.Scaling(1, 1, -1) * Matrix.RotationYawPitchRoll(0, d90, 0);

            AddModelToObj(obj, model, matrix, new[] { Program.Arguments.NifLayer }, false);
            if (obj.MeshCount == 0)
            {
                AddModelToObj(obj, model, matrix, new string[0], true);
            }
            return(obj);
        }
示例#2
0
        public void Dispose()
        {
            if (ObjWriter == null)
            {
                return;
            }

            DoorWriter.Flush();
            DoorWriter.Dispose();
            GeomSetWriter.Flush();
            GeomSetWriter.Dispose();
            ObjWriter.Save();
            if (ObjWriter.Empty)
            {
                File.Delete(ObjWriter.File);
            }
            ObjWriter = null;
        }
示例#3
0
        public Zone2Obj(Zone2 zone)
        {
            Zone = zone;
            if (!Directory.Exists("zones"))
            {
                Directory.CreateDirectory("zones");
            }
            string filename = Path.Combine("zones", string.Format("zone{0:D3}", zone.ID));

            DoorWriter    = new DoorWriter(filename + ".doors");
            GeomSetWriter = new GeomSetWriter(filename + ".geomset");
            ObjWriter     = new WavefrontObjFile(filename + ".obj")
            {
                Scale = MESH_SCALE
            };
            GeomSetWriter.WriteLoadMesh(filename + ".obj");
            FirstPass = !NavmeshMgr.IsPathingEnabled(zone);
        }
示例#4
0
        private static LosTreeType _LoadZone(Region region, Zone zone, string filename)
        {
            var(vertices, objects) = WavefrontObjFile.Load(zone, filename);
            if (vertices == null || vertices.Length == 0 || objects == null)
            {
                return(null);
            }

            var zoneMin = new Vector3(float.PositiveInfinity);
            var zoneMax = new Vector3(float.NegativeInfinity);

            foreach (var v in vertices)
            {
                if (v.Z <= 0 || v.Z > 65530)
                {
                    continue;
                }
                zoneMin = Vector3.Min(zoneMin, v);
                zoneMax = Vector3.Max(zoneMax, v);
            }
            zoneMin.Z -= 500;
            zoneMax.Z += 500;

            var zoneTree = new LosTreeType(new AABoundingBox(zoneMin, zoneMax), 1);

            foreach (var faces in objects)
            {
                foreach (var(a, b, c) in faces)
                {
                    zoneTree.AddObject(new Triangle(vertices, a, b, c));
                }
            }
            if (log.IsDebugEnabled)
            {
                log.Debug($"[LosMgr] Zone {zone.ZoneSkinID} loaded: {objects.Count:N0} objects {objects.Select(o => o.Length).Sum():N0} faces {vertices.Length:N0} vertices");
            }
            return(zoneTree);
        }
示例#5
0
        public static void AddModelToObj(WavefrontObjFile objFile, NiFile model, Matrix worldMatrix, string[] filter, bool exclude)
        {
            if (model == null)
            {
                return;
            }

            bool foundMesh = false;

            // find all trimeshs and tristrips
            foreach (NiObject obj in model.ObjectsByRef.Values)
            {
                var avNode = obj as NiAVObject;
                if (avNode == null || ((exclude && IsFiltered(avNode, filter)) || (!exclude && !IsFiltered(avNode, filter))))
                {
                    continue;
                }

                var shape = obj as NiTriShape;
                if (shape != null)
                {
                    eFaceDrawMode mode = FindDrawMode(shape);
                    foundMesh = true;
                    Matrix myMatrix = ComputeWorldMatrix(shape) * worldMatrix;

                    var data = shape.Data.Object as NiTriShapeData;
                    if (data.Triangles.Length == 0)
                    {
                        continue;
                    }

                    var transformedVertices = new Vector3[data.Vertices.Length];

                    for (int i = 0; i < data.Vertices.Length; i++)
                    {
                        Vector4 transformedVector = Vector3.Transform(data.Vertices[i], myMatrix);
                        transformedVertices[i] = new Vector3(transformedVector.X, transformedVector.Y, transformedVector.Z);
                    }

                    var triangles = new List <Triangle>();

                    // CCW
                    if (mode == eFaceDrawMode.DRAW_BOTH ||
                        mode == eFaceDrawMode.DRAW_CCW ||
                        mode == eFaceDrawMode.DRAW_CCW_OR_BOTH)
                    {
                        for (int i = 0; i < data.Triangles.Length; i++)
                        {
                            triangles.Add(new Triangle(data.Triangles[i].Z, data.Triangles[i].Y, data.Triangles[i].X));
                        }
                    }

                    // CC
                    if (mode == eFaceDrawMode.DRAW_BOTH ||
                        mode == eFaceDrawMode.DRAW_CW)
                    {
                        foreach (Triangle t in data.Triangles)
                        {
                            triangles.Add(t);
                        }
                    }

                    objFile.AddMesh(transformedVertices, triangles.ToArray());
                }

                var strips = obj as NiTriStrips;
                if (strips != null)
                {
                    eFaceDrawMode mode = FindDrawMode(strips);
                    foundMesh = true;
                    Matrix myMatrix = ComputeWorldMatrix(strips) * worldMatrix;

                    var data = strips.Data.Object as NiTriStripsData;

                    var transformedVertices = new Vector3[data.Vertices.Length];

                    for (int i = 0; i < data.Vertices.Length; i++)
                    {
                        Vector4 transformedVector = Vector3.Transform(data.Vertices[i], myMatrix);
                        transformedVertices[i] = new Vector3(transformedVector.X, transformedVector.Y,
                                                             transformedVector.Z);
                    }


                    var triangles = new List <Triangle>();

                    foreach (var points in data.Points)
                    {
                        // CCW
                        if (mode == eFaceDrawMode.DRAW_BOTH ||
                            mode == eFaceDrawMode.DRAW_CCW ||
                            mode == eFaceDrawMode.DRAW_CCW_OR_BOTH)
                        {
                            for (int i = 0; i < points.Length - 2; i++)
                            {
                                triangles.Add(i % 2 == 0
                                ? new Triangle(points[i + 2], points[i + 1], points[i + 0])
                                : new Triangle(points[i + 2], points[i + 0], points[i + 1]));
                            }
                        }

                        // CC
                        if (mode == eFaceDrawMode.DRAW_BOTH ||
                            mode == eFaceDrawMode.DRAW_CW)
                        {
                            for (int i = 0; i < points.Length - 2; i++)
                            {
                                triangles.Add(i % 2 == 0
                                ? new Triangle(points[i + 0], points[i + 1], points[i + 2])
                                : new Triangle(points[i + 0], points[i + 2], points[i + 1]));
                            }
                        }
                    }


                    objFile.AddMesh(transformedVertices, triangles.ToArray());
                }
            }

            if (!foundMesh && filter[0] == "pickee")
            {
                // no pickee found, use collide
                Console.WriteLine("Warning: Using collidee!");
                AddModelToObj(objFile, model, worldMatrix, new[] { "collide" }, false);
            }
        }