Esempio n. 1
0
        public static KtxFile Load(File file, bool readKeyValuePairs)
        {
            KtxHeader header = ReadStruct <KtxHeader>(file);

            KtxKeyValuePair[] kvps = null;
            if (readKeyValuePairs)
            {
                int keyValuePairBytesRead            = 0;
                List <KtxKeyValuePair> keyValuePairs = new List <KtxKeyValuePair>();
                while (keyValuePairBytesRead < header.BytesOfKeyValueData)
                {
                    int             bytesRemaining = (int)(header.BytesOfKeyValueData - keyValuePairBytesRead);
                    KtxKeyValuePair kvp            = ReadNextKeyValuePair(file, out int read);
                    keyValuePairBytesRead += read;
                    keyValuePairs.Add(kvp);
                }

                kvps = keyValuePairs.ToArray();
            }
            else
            {
                file.Skip((int)header.BytesOfKeyValueData); // Skip over header data.
            }

            uint numberOfMipmapLevels  = Math.Max(1, header.NumberOfMipmapLevels);
            uint numberOfArrayElements = Math.Max(1, header.NumberOfArrayElements);
            uint numberOfFaces         = Math.Max(1, header.NumberOfFaces);

            uint        baseWidth  = Math.Max(1, header.PixelWidth);
            uint        baseHeight = Math.Max(1, header.PixelHeight);
            uint        baseDepth  = Math.Max(1, header.PixelDepth);
            List <uint> imageSizes = new List <uint>();

            MipmapLevel[] images = new MipmapLevel[numberOfMipmapLevels];

            long dataSize  = file.Length - file.Position;
            uint totalSize = 0;

            for (int mip = 0; mip < numberOfMipmapLevels; mip++)
            {
                uint mipWidth  = Math.Max(1, baseWidth / (uint)(Math.Pow(2, mip)));
                uint mipHeight = Math.Max(1, baseHeight / (uint)(Math.Pow(2, mip)));
                uint mipDepth  = Math.Max(1, baseDepth / (uint)(Math.Pow(2, mip)));

                uint imageSize = file.Read <uint>();

                if (mip == 11)
                {
                    //bug?
                    imageSize = Math.Min(imageSizes.Back() >> 2, imageSize);
                    //imageSize = 1;
                }

                imageSizes.Add(imageSize);
                ArrayElement[] arrayElements = new ArrayElement[numberOfArrayElements];
                bool           isCubemap     = header.NumberOfFaces == 6 && header.NumberOfArrayElements == 0;

                uint arrayElementSize = imageSize / numberOfArrayElements;

                for (int arr = 0; arr < numberOfArrayElements; arr++)
                {
                    uint        faceSize = arrayElementSize;
                    ImageFace[] faces    = new ImageFace[numberOfFaces];
                    for (int face = 0; face < numberOfFaces; face++)
                    {
                        faces[face] = new ImageFace(file.ReadBytes((int)faceSize));
                        uint cubePadding = 0u;
                        if (isCubemap)
                        {
                            cubePadding = 3 - ((imageSize + 3) % 4);
                        }

                        file.Skip((int)cubePadding);
                        totalSize += faceSize;
                    }

                    arrayElements[arr] = new ArrayElement(faces);
                }

                images[mip] = new MipmapLevel(
                    mipWidth,
                    mipHeight,
                    mipDepth,
                    imageSize,
                    arrayElements, header.NumberOfArrayElements);

                uint mipPaddingBytes = 3 - ((imageSize + 3) % 4);
                //Debug.Assert(mipPaddingBytes == 0);
                file.Skip((int)mipPaddingBytes);
            }

            //Debug.Assert(dataSize == numberOfMipmapLevels * 4 + totalSize);

            return(new KtxFile(header, kvps, images));
        }
Esempio n. 2
0
 public KtxFile(KtxHeader header, KtxKeyValuePair[] keyValuePairs, MipmapLevel[] mipmaps)
 {
     Header        = header;
     KeyValuePairs = keyValuePairs;
     Mipmaps       = mipmaps;
 }