Exemple #1
0
        public void Export(Stream stream)
        {
            BinaryWriter writer = new BinaryWriter(stream);

            byte[] buffer = null;
            switch (m_TextureFormat)
            {
            case TextureFormat.DXT1:
            case TextureFormat.DXT5:
                byte[] dds_header = DDS.CreateHeader(m_Width, m_Height, 32, m_MipMap ? 2 : 0, m_TextureFormat);
                writer.Write(dds_header);
                buffer = image_data;
                break;

            case TextureFormat.RGB24:
                byte[] tga_header = TGA.CreateHeader((ushort)m_Width, (ushort)m_Height, 24);
                writer.Write(tga_header);
                buffer = new byte[image_data.Length];
                for (int i = 0, j = 2; j < m_CompleteImageSize; i += 3, j += 3)
                {
                    byte b = image_data[j];
                    buffer[j]     = image_data[i];
                    buffer[i]     = b;
                    buffer[i + 1] = image_data[i + 1];
                }
                break;

            case TextureFormat.ARGB32:
                tga_header = TGA.CreateHeader((ushort)m_Width, (ushort)m_Height, 32);
                writer.Write(tga_header);
                buffer = new byte[image_data.Length];
                for (int i = 0, j = 3, k = 1, l = 2; j < m_CompleteImageSize; i += 4, j += 4, k += 4, l += 4)
                {
                    byte b = image_data[j];
                    buffer[j] = image_data[i];
                    buffer[i] = b;
                    b         = image_data[l];
                    buffer[l] = image_data[k];
                    buffer[k] = b;
                }
                break;

            case TextureFormat.Alpha8:
                tga_header = TGA.CreateHeader((ushort)m_Width, (ushort)m_Height, 8);
                writer.Write(tga_header);
                buffer = (byte[])image_data.Clone();
                break;

            case TextureFormat.RGBA32:
                tga_header = TGA.CreateHeader((ushort)m_Width, (ushort)m_Height, 32);
                writer.Write(tga_header);
                buffer = (byte[])image_data.Clone();
                break;

            default:
                throw new Exception("Unhandled Texture2D format: " + m_TextureFormat);
            }
            writer.Write(buffer);
        }
Exemple #2
0
            public static Texture2D ToImage(ImportedTexture tex, ImageLoadInformation loadInfo, out byte pixelDepth)
            {
                ushort width, height;

                byte[] data;
                using (Stream stream = new MemoryStream(tex.Data))
                {
                    byte  idLen, descriptor;
                    bool  compressed;
                    short originY;
                    GetImageInfo(stream, out idLen, out compressed, out originY, out width, out height, out pixelDepth, out descriptor);
                    if (compressed)
                    {
                        throw new Exception("Warning! Compressed TGAs are not supported");
                    }
                    stream.Position = idLen + 0x12;
                    BinaryReader reader = new BinaryReader(stream);
                    data = reader.ReadToEnd();
                    if (originY == 0)
                    {
                        Flip((short)height, width, height, (byte)(pixelDepth >> 3), data);
                    }
                }
                byte[] header = DDS.CreateHeader(width, height, pixelDepth, 0, false, pixelDepth == 32 ? DDS.UnityCompatibleFormat.ARGB32 : DDS.UnityCompatibleFormat.RGB24);
                using (BinaryWriter writer = new BinaryWriter(new MemoryStream()))
                {
                    writer.Write(header);
                    writer.Write(data);

                    try
                    {
                        writer.BaseStream.Position = 0;
                        return(Texture2D.FromStream(Gui.Renderer.Device, writer.BaseStream, (int)writer.BaseStream.Length, loadInfo));
                    }
                    catch (Exception e)
                    {
                        Direct3D11Exception d3de = e as Direct3D11Exception;
                        if (d3de != null)
                        {
                            Report.ReportLog("Direct3D11 Exception name=\"" + d3de.ResultCode.Name + "\" desc=\"" + d3de.ResultCode.Description + "\" code=0x" + ((uint)d3de.ResultCode.Code).ToString("X"));
                        }
                        else
                        {
                            Utility.ReportException(e);
                        }
                        return(null);
                    }
                }
            }
Exemple #3
0
        public void Export(Stream stream)
        {
            BinaryWriter writer = new BinaryWriter(stream);

            byte[] buffer = null;
            switch (m_TextureFormat)
            {
            case TextureFormat.DXT1:
            case TextureFormat.DXT5:
                byte[] dds_header = DDS.CreateHeader(m_Width, m_Height, 32, m_MipMap ? 2 : 0,
                                                     m_TextureFormat == TextureFormat.DXT1
                                        ? (byte)'D' | ((byte)'X' << 8) | ((byte)'T' << 16) | ((byte)'1' << 24)
                                        : (byte)'D' | ((byte)'X' << 8) | ((byte)'T' << 16) | ((byte)'5' << 24));
                writer.Write(dds_header);
                buffer = image_data;
                break;

            case TextureFormat.RGB24:
                byte[] tga_header = new byte[0x12]
                {
                    0, 0, 2, 0, 0, 0, 0, 0, 0, 0, 0, 0,
                    (byte)m_Width, (byte)(m_Width >> 8), (byte)m_Height, (byte)(m_Height >> 8), 24, 0
                };
                writer.Write(tga_header);
                buffer = new byte[image_data.Length];
                for (int i = 0, j = 2; j < m_CompleteImageSize; i += 3, j += 3)
                {
                    byte b = image_data[j];
                    buffer[j]     = image_data[i];
                    buffer[i]     = b;
                    buffer[i + 1] = image_data[i + 1];
                }
                break;

            case TextureFormat.ARGB32:
                tga_header = new byte[0x12]
                {
                    0, 0, 2, 0, 0, 0, 0, 0, 0, 0, 0, 0,
                    (byte)m_Width, (byte)(m_Width >> 8), (byte)m_Height, (byte)(m_Height >> 8), 32, 0
                };
                writer.Write(tga_header);
                buffer = new byte[image_data.Length];
                for (int i = 0, j = 3, k = 1, l = 2; j < m_CompleteImageSize; i += 4, j += 4, k += 4, l += 4)
                {
                    byte b = image_data[j];
                    buffer[j] = image_data[i];
                    buffer[i] = b;
                    b         = image_data[l];
                    buffer[l] = image_data[k];
                    buffer[k] = b;
                }
                break;

            case TextureFormat.Alpha8:
                tga_header = new byte[0x12]
                {
                    0, 0, 2, 0, 0, 0, 0, 0, 0, 0, 0, 0,
                    (byte)m_Width, (byte)(m_Width >> 8), (byte)m_Height, (byte)(m_Height >> 8), 8, 0
                };
                writer.Write(tga_header);
                buffer = (byte[])image_data.Clone();
                break;

            default:
                throw new Exception("Unhandled Texture2D format: " + m_TextureFormat);
            }
            writer.Write(buffer);
        }
Exemple #4
0
            public static Texture2D ScaleWhenNeeded(byte[] file_data, out int originalWidth, out int originalHeight, out int BPP, out bool cubemap)
            {
                uint[] fileHeader;
                int    mipmaps;
                uint   pixelFormat;
                uint   fourCC;
                UnityCompatibleFormat format;

                uint[] dx10Header = null;
                using (BinaryReader reader = new BinaryReader(new MemoryStream(file_data)))
                {
                    fileHeader     = reader.ReadUInt32Array(32);
                    originalWidth  = (int)fileHeader[4];
                    originalHeight = (int)fileHeader[3];
                    mipmaps        = (int)fileHeader[7];
                    pixelFormat    = fileHeader[20];
                    fourCC         = fileHeader[21];
                    if ((pixelFormat & (uint)DDS_PIXEL_FORMAT.DDPF_FOURCC) != 0 && fourCC == FOURCC_DX10)
                    {
                        dx10Header = reader.ReadUInt32Array(5);
                        fourCC     = dx10Header[0];
                    }
                    format = (pixelFormat & (uint)DDS_PIXEL_FORMAT.DDPF_FOURCC) != 0
                                                ? fourCC == FOURCC_DXT1 ? UnityCompatibleFormat.DXT1
                                                        : fourCC == FOURCC_DXT5 ? UnityCompatibleFormat.DXT5
                                                                : fourCC == (uint)SlimDX.Direct3D9.Format.A32B32G32R32F ? UnityCompatibleFormat.RGBAFloat
                                                                        : fourCC == (uint)SlimDX.Direct3D9.Format.A16B16G16R16F ? UnityCompatibleFormat.RGBAHalf
                                                                                : fourCC == (uint)SlimDX.DXGI.Format.BC7_UNorm ? UnityCompatibleFormat.BC7
                                                                                        : (UnityCompatibleFormat)(-1)
                                                : (pixelFormat & (uint)DDS_PIXEL_FORMAT.DDPF_ALPHAPIXELS) != 0
                                                        ? UnityCompatibleFormat.ARGB32 : UnityCompatibleFormat.RGB24;
                    cubemap = fileHeader[28] == (uint)(DDS_CAPS2.DDSCAPS2_CUBEMAP | DDS_CAPS2.DDS_CUBEMAP_ALLFACES);
                }
                if (format == (UnityCompatibleFormat)(-1))
                {
                    throw new Exception("Unsupported DDS format - FourCC x" + fourCC.ToString("X"));
                }
                if ((format == UnityCompatibleFormat.ARGB32 || format == UnityCompatibleFormat.RGB24) &&
                    (fileHeader[23] != 0x00ff0000 || fileHeader[24] != 0x0000ff00 || fileHeader[25] != 0x000000ff))
                {
                    throw new Exception("Unsupported DDS channel order or usage");
                }
                if (format == UnityCompatibleFormat.RGB24 && fileHeader[26] != 0 ||
                    format == UnityCompatibleFormat.ARGB32 && fileHeader[26] != 0xff000000)
                {
                    Report.ReportLog("Warning! Wrong DDS channel order or usage");
                }
                switch (format)
                {
                case UnityCompatibleFormat.RGB24:
                    BPP = 24;
                    break;

                case UnityCompatibleFormat.RGBAHalf:
                    BPP = 64;
                    break;

                case UnityCompatibleFormat.RGBAFloat:
                    BPP = 128;
                    break;

                default:
                    BPP = 32;
                    break;
                }

                byte[] buffer;
                int    maxDim = cubemap ? 256 : 1024;

                if (originalWidth > maxDim || originalHeight > maxDim || cubemap)
                {
                    int divSize = (pixelFormat & (uint)DDS_PIXEL_FORMAT.DDPF_FOURCC) != 0 &&
                                  (fourCC == FOURCC_DXT1 || fourCC == FOURCC_DXT5) ? 4 : 1;
                    int blockBytes = (pixelFormat & (uint)DDS_PIXEL_FORMAT.DDPF_FOURCC) != 0
                                                ? format == UnityCompatibleFormat.DXT1 || format == UnityCompatibleFormat.RGBAHalf ? 8
                                                        : format == UnityCompatibleFormat.DXT5 || format == UnityCompatibleFormat.RGBAFloat ? 16
                                                                : -1
                                                : (pixelFormat & (uint)DDS_PIXEL_FORMAT.DDPF_ALPHAPIXELS) != 0 ? 4 : 3;
                    if (blockBytes <= 0)
                    {
                        buffer = file_data;
                    }
                    else
                    {
                        int src = fileHeader.Length * sizeof(uint) + (dx10Header != null ? dx10Header.Length * sizeof(uint) : 0);
                        int dst = 0;
                        buffer = null;
                        int imgSize       = (file_data.Length - src) / (cubemap ? 6 : 1);
                        int srcBlockWidth = Math.Max(divSize, (originalWidth + divSize - 1)) / divSize;
                        for (int i = 0; i < (cubemap ? 6 : 1); i++)
                        {
                            int width = originalWidth, blockWidth;
                            int height = originalHeight, blockHeight;
                            int blocks;
                            int mipStart = src;
                            int shift    = 0;
                            while (width > maxDim || height > maxDim)
                            {
                                blockWidth  = Math.Max(divSize, (width + divSize - 1)) / divSize;
                                blockHeight = Math.Max(divSize, (height + divSize - 1)) / divSize;
                                blocks      = blockWidth * blockHeight;
                                mipStart   += blocks * blockBytes;

                                if (width > 1)
                                {
                                    width >>= 1;
                                }
                                if (height > 1)
                                {
                                    height >>= 1;
                                }
                                shift++;
                            }
                            blockWidth  = Math.Max(divSize, (width + divSize - 1)) / divSize;
                            blockHeight = Math.Max(divSize, (height + divSize - 1)) / divSize;
                            blocks      = blockWidth * blockHeight;
                            int size = blocks * blockBytes;
                            if (i == 0)
                            {
                                byte[] header = DDS.CreateHeader(width, height * (cubemap ? 6 : 1), BPP, 0, false, format);
                                buffer = new byte[header.Length + size * (cubemap ? 6 : 1)];
                                Array.Copy(header, buffer, header.Length);
                                dst = header.Length;
                            }
                            if (mipmaps <= 1)
                            {
                                int imgSrc      = src;
                                int srcLineRest = srcBlockWidth * blockBytes - (blockBytes << shift) * blockWidth;
                                for (int y = 0; y < blockHeight; y++)
                                {
                                    for (int x = 0; x < blockWidth; x++)
                                    {
                                        Array.Copy(file_data, imgSrc, buffer, dst, blockBytes);
                                        imgSrc += blockBytes << shift;
                                        dst    += blockBytes;
                                    }
                                    imgSrc += srcLineRest + ((1 << shift) - 1) * srcBlockWidth * blockBytes;
                                }
                            }
                            else
                            {
                                Array.Copy(file_data, mipStart, buffer, dst, size);
                                dst += size;
                            }
                            src += imgSize;
                        }
                    }
                }
                else
                {
                    buffer = file_data;
                }

                ImageLoadInformation loadInfo = new ImageLoadInformation()
                {
                    BindFlags      = BindFlags.None,
                    CpuAccessFlags = CpuAccessFlags.Read,
                    FilterFlags    = FilterFlags.None,
                    Format         = Format.R8G8B8A8_UNorm,
                    MipFilterFlags = FilterFlags.None,
                    MipLevels      = 0,
                    OptionFlags    = ResourceOptionFlags.None,
                    Usage          = ResourceUsage.Staging,
                };

                return(Texture2D.FromMemory(Gui.Renderer.Device, buffer, loadInfo));
            }