예제 #1
0
        public void FinalizeVertices(LightmapResource lightmap, bool regen)
        {
            _lightmapcoords = new float[_bspVertices.Count * 2];

            for (int i = 0; i < _surfaces.Length; i++)
            {
                if (i == 45)
                {
                    i = i;
                }

                for (int j = 0; j < _surfaces[i].indices.Length; j++)
                {
                    float u = (_surfaces[i].uCoord + _texcoords[_surfaces[i].indices[j] * 2 + 0]) * _surfaces[i].uScale;
                    float v = (_surfaces[i].vCoord + _texcoords[_surfaces[i].indices[j] * 2 + 1]) * _surfaces[i].vScale;

                    //_lightmapcoords[_surfaces[i].indices[j] * 2 + 0] = u;
                    //_lightmapcoords[_surfaces[i].indices[j] * 2 + 1] = v;

                    _lightmapcoords[(_surfaces[i].VertexIndex + j) * 2 + 0] = u;
                    _lightmapcoords[(_surfaces[i].VertexIndex + j) * 2 + 1] = v;

                    if (lightmap != null)
                    {
                        Rect lightmapRect = lightmap.PackedLightmaps.GetPackedTextureRect(i);

                        //_lightmapcoords[_surfaces[i].indices[j] * 2 + 0] += 1.0f / lightmapRect.Width * 0.5f;
                        //_lightmapcoords[_surfaces[i].indices[j] * 2 + 1] += 1.0f / lightmapRect.Height * 0.5f;

                        float lu = (lightmapRect.X + 0.5f) / lightmap.PackedLightmapTexture.Width;
                        float lv = (lightmapRect.Y + 0.5f) / lightmap.PackedLightmapTexture.Height;
                        float lw = (lightmapRect.Width - 1.0f) / lightmap.PackedLightmapTexture.Width;
                        float lh = (lightmapRect.Height - 1.0f) / lightmap.PackedLightmapTexture.Height;

                        BspVertex vertex = _bspVertices[_surfaces[i].VertexIndex + j];
                        vertex.LU = lu + u * lw;
                        vertex.LV = lv + v * lh;
                        _bspVertices[_surfaces[i].VertexIndex + j] = vertex;
                    }
                    else
                    {
                        BspVertex vertex = _bspVertices[_surfaces[i].VertexIndex + j];
                        vertex.LU = u;
                        vertex.LV = v;
                        _bspVertices[_surfaces[i].VertexIndex + j] = vertex;
                    }
                }
            }

            _allVertices = RendererManager.CurrentRenderer.CreateVertexBuffer(VertexBufferUsage.Static, _bspVertices.ToArray(), _bspVertices.Count, _vertexDeclaration);
        }
예제 #2
0
        public BspResource(string name, System.IO.Stream stream, Resource.ResourceManager content)
            : base(name, true)
        {
            System.IO.BinaryReader reader =
                new System.IO.BinaryReader(stream);

            // read the header
            BspHeader header = new BspHeader();

            header.heading          = reader.ReadBytes(4);
            header.minorVersion     = reader.ReadUInt16();
            header.majorVersion     = reader.ReadUInt16();
            header.dataSectionSize  = reader.ReadUInt32();
            header.rootIndex        = reader.ReadUInt32();
            header.numModels        = reader.ReadUInt32();
            header.numVertices      = reader.ReadUInt32();
            header.numTexCoords     = reader.ReadUInt32();
            header.numVertexIndices = reader.ReadUInt32();
            header.numTexIndices    = reader.ReadUInt32();
            header.numSurfaces      = reader.ReadUInt32();
            header.numPlanes        = reader.ReadUInt32();
            header.numNodes         = reader.ReadUInt32();
            header.numPolygons      = reader.ReadUInt32();

            // read the model names
            byte[]     buffer32 = new byte[32];
            BspModel[] models   = new BspModel[header.numModels];
            _modelsNames = new string[header.numModels];
            for (uint i = 0; i < header.numModels; i++)
            {
                models[i] = new BspModel();

                models[i].name  = Gk3Main.Utils.ConvertAsciiToString(reader.ReadBytes(32));
                _modelsNames[i] = models[i].name;
            }

            // read the surfaces
            Random randomGenerator = new Random();

            _surfaces = new BspSurface[header.numSurfaces];
            for (uint i = 0; i < header.numSurfaces; i++)
            {
                if (i == 134)
                {
                    i = i;
                }

                _surfaces[i] = new BspSurface();

                _surfaces[i].modelIndex = reader.ReadUInt32();
                _surfaces[i].texture    = Gk3Main.Utils.ConvertAsciiToString(reader.ReadBytes(32));
                _surfaces[i].uCoord     = reader.ReadSingle();
                _surfaces[i].vCoord     = reader.ReadSingle();
                _surfaces[i].uScale     = reader.ReadSingle();
                _surfaces[i].vScale     = reader.ReadSingle();
                _surfaces[i].size1      = reader.ReadUInt16();
                _surfaces[i].size2      = reader.ReadUInt16();
                _surfaces[i].flags      = (BspSurfaceFlags)reader.ReadUInt32();

                _surfaces[i].r     = (float)randomGenerator.NextDouble();
                _surfaces[i].g     = (float)randomGenerator.NextDouble();
                _surfaces[i].b     = (float)randomGenerator.NextDouble();
                _surfaces[i].index = i;
            }

            // read the BSP nodes (for now throw them away)
            _nodes = new BspNode[header.numNodes];
            for (uint i = 0; i < header.numNodes; i++)
            {
                _nodes[i].Left              = reader.ReadInt16();
                _nodes[i].Right             = reader.ReadInt16();
                _nodes[i].PlaneIndex        = reader.ReadInt16();
                _nodes[i].PolygonStartIndex = reader.ReadInt16();
                reader.ReadInt16();
                _nodes[i].NumPolygons = reader.ReadInt16();

                uint i3 = reader.ReadUInt16();
                uint i4 = reader.ReadUInt16();
            }

            // TEMP: validate the BSP
            foreach (BspNode node in _nodes)
            {
                if (node.Left >= _nodes.Length ||
                    node.Right >= _nodes.Length)
                {
                    throw new Exception("OH NO!");
                }
            }

            int parent = findParent(_nodes, 0);

            // read all the polygons
            _polygons = new BspPolygon[header.numPolygons];
            for (uint i = 0; i < header.numPolygons; i++)
            {
                _polygons[i] = new BspPolygon();

                _polygons[i].vertexIndex  = reader.ReadUInt16();
                _polygons[i].flags        = reader.ReadUInt16();
                _polygons[i].numVertices  = reader.ReadUInt16();
                _polygons[i].surfaceIndex = reader.ReadUInt16();

                if (_polygons[i].surfaceIndex == 134)
                {
                    i = i;
                }
            }

            // read all the planes (thow them away)
            for (uint i = 0; i < header.numPlanes; i++)
            {
                reader.ReadBytes(16);
            }

            // read the vertices
            _vertices = new float[header.numVertices * 3];
            for (uint i = 0; i < header.numVertices; i++)
            {
                _vertices[i * 3 + 0] = reader.ReadSingle();
                _vertices[i * 3 + 1] = reader.ReadSingle();
                _vertices[i * 3 + 2] = reader.ReadSingle();
            }

            // read the texture vertices
            _texcoords = new float[header.numTexCoords * 2];
            for (uint i = 0; i < header.numTexCoords; i++)
            {
                _texcoords[i * 2 + 0] = reader.ReadSingle();
                _texcoords[i * 2 + 1] = reader.ReadSingle();
            }

            // read all the vertex indices
            ushort[] indices = new ushort[header.numVertexIndices];
            for (uint i = 0; i < header.numVertexIndices; i++)
            {
                indices[i] = reader.ReadUInt16();
            }

            // read all the texcoord indices
            ushort[] texindices = new ushort[header.numTexIndices];
            for (uint i = 0; i < header.numTexIndices; i++)
            {
                texindices[i] = reader.ReadUInt16();
            }

            // read the bounding spheres
            _boundingSpheres = new Math.Vector4[header.numNodes];
            for (uint i = 0; i < header.numNodes; i++)
            {
                _boundingSpheres[i].Z = reader.ReadSingle();
                _boundingSpheres[i].Y = reader.ReadSingle();
                _boundingSpheres[i].X = reader.ReadSingle();
                _boundingSpheres[i].W = reader.ReadSingle();
            }

            // load the "thingies", whatever that means
            _bspVertices = new List <BspVertex>();
            for (int i = 0; i < header.numSurfaces; i++)
            {
                // throw junk away
                _surfaces[i].boundingSphere.X = reader.ReadSingle();
                _surfaces[i].boundingSphere.Y = reader.ReadSingle();
                _surfaces[i].boundingSphere.Z = reader.ReadSingle();
                _surfaces[i].boundingSphere.W = reader.ReadSingle();

                reader.ReadBytes(12);

                uint numIndices = reader.ReadUInt32();
                _surfaces[i].numTriangles = reader.ReadUInt32();

                UInt16[] myindices = new UInt16[numIndices];
                for (uint j = 0; j < numIndices; j++)
                {
                    myindices[j] = reader.ReadUInt16();
                }

                _surfaces[i].VertexIndex = _bspVertices.Count;
                _surfaces[i].indices     = new ushort[_surfaces[i].numTriangles * 3];
                for (uint j = 0; j < _surfaces[i].numTriangles; j++)
                {
                    ushort x = reader.ReadUInt16();
                    ushort y = reader.ReadUInt16();
                    ushort z = reader.ReadUInt16();

                    _surfaces[i].indices[j * 3 + 0] = myindices[x];
                    _surfaces[i].indices[j * 3 + 1] = myindices[y];
                    _surfaces[i].indices[j * 3 + 2] = myindices[z];

                    // TODO: since we aren't using indices the hardware can't cache vertices,
                    // so there's some performance loss. Figure out a good way to still use indices.

                    // vertex 1
                    BspVertex vertex = new BspVertex();
                    vertex.X = _vertices[myindices[x] * 3 + 0];
                    vertex.Y = _vertices[myindices[x] * 3 + 1];
                    vertex.Z = _vertices[myindices[x] * 3 + 2];
                    vertex.U = _texcoords[myindices[x] * 2 + 0];
                    vertex.V = _texcoords[myindices[x] * 2 + 1];
                    _bspVertices.Add(vertex);

                    // vertex 2
                    vertex.X = _vertices[myindices[y] * 3 + 0];
                    vertex.Y = _vertices[myindices[y] * 3 + 1];
                    vertex.Z = _vertices[myindices[y] * 3 + 2];
                    vertex.U = _texcoords[myindices[y] * 2 + 0];
                    vertex.V = _texcoords[myindices[y] * 2 + 1];
                    _bspVertices.Add(vertex);

                    // vertex 3
                    vertex.X = _vertices[myindices[z] * 3 + 0];
                    vertex.Y = _vertices[myindices[z] * 3 + 1];
                    vertex.Z = _vertices[myindices[z] * 3 + 2];
                    vertex.U = _texcoords[myindices[z] * 2 + 0];
                    vertex.V = _texcoords[myindices[z] * 2 + 1];
                    _bspVertices.Add(vertex);
                }
                _surfaces[i].VertexCount = _bspVertices.Count - _surfaces[i].VertexIndex;
            }

            reader.Close();

            loadTextures(content);
        }