예제 #1
0
        public virtual FileMap EncodeTEX0Texture(Bitmap src, int mipLevels)
        {
            int w = src.Width, h = src.Height;
            int bw = BlockWidth, bh = BlockHeight;

            PixelFormat fmt = src.IsIndexed() ? src.PixelFormat : PixelFormat.Format32bppArgb;

            FileMap fileView = FileMap.FromTempFile(GetFileSize(w, h, mipLevels) + 0x40);

            try
            {
                //Build TEX header
                TEX0v1 *header = (TEX0v1 *)fileView.Address;
                *       header = new TEX0v1(w, h, RawFormat, mipLevels);

                int sStep = bw * Image.GetPixelFormatSize(fmt) / 8;
                int dStep = bw * bh * BitsPerPixel / 8;

                using (DIB dib = DIB.FromBitmap(src, bw, bh, fmt))
                    for (int i = 1; i <= mipLevels; i++)
                    {
                        EncodeLevel(header->PixelData, dib, src, dStep, sStep, i);
                    }

                return(fileView);
            }
            catch (Exception x)
            {
                MessageBox.Show(x.ToString());
                fileView.Dispose();
                return(null);
            }
        }
예제 #2
0
        public unsafe virtual void ReplaceRaw(VoidPtr address, int length)
        {
            FileMap map = FileMap.FromTempFile(length);

            Memory.Move(map.Address, address, (uint)length);
            ReplaceRaw(map);
        }
예제 #3
0
        public virtual void Rebuild(bool force)
        {
            if (!IsDirty && !force)
            {
                return;
            }

            //Get uncompressed size
            int size = OnCalculateSize(force);

            //Create temp map
            FileMap uncompMap = FileMap.FromTempFile(size);

            //Rebuild node (uncompressed)
            Rebuild(uncompMap.Address, size, force);
            _replSrc.Map = _replUncompSrc.Map = uncompMap;

            //If compressed, compress resulting data.
            if (_compression != CompressionType.None)
            {
                //Compress node to temp file
                FileStream stream = new FileStream(Path.GetTempFileName(), FileMode.Open, FileAccess.ReadWrite, FileShare.None, 0x8, FileOptions.DeleteOnClose | FileOptions.SequentialScan);
                try
                {
                    Compressor.Compact(_compression, uncompMap.Address, uncompMap.Length, stream);
                    _replSrc = new DataSource(FileMap.FromStreamInternal(stream, FileMapProtect.Read, 0, (int)stream.Length), _compression);
                }
                catch (Exception x) { stream.Dispose(); throw x; }
            }
        }
예제 #4
0
        public static unsafe ResourceNode FromSource(ResourceNode parent, DataSource source)
        {
            ResourceNode n = null;

            if ((n = GetRaw(source)) != null)
            {
                n.Initialize(parent, source);
            }
            else
            {
                //Check for compression?
                if (Compressor.IsDataCompressed(source.Address, source.Length))
                {
                    if ((*(uint *)source.Address) == YAZ0.Tag)
                    {
                        YAZ0 *cmpr = (YAZ0 *)source.Address;
                        try
                        {
                            //Expand the whole resource and initialize
                            FileMap map = FileMap.FromTempFile((int)cmpr->_unCompDataLen);
                            Compressor.Expand(cmpr, map.Address, map.Length);
                            source.Compression = CompressionType.RunLength;

                            //Check for a match
                            if ((n = GetRaw(new DataSource(map.Address, map.Length))) != null)
                            {
                                n.Initialize(parent, source, new DataSource(map));
                            }
                        }
                        catch (InvalidCompressionException e) { MessageBox.Show(e.ToString()); }
                    }
                    else
                    {
                        CompressionHeader *cmpr = (CompressionHeader *)source.Address;
                        if (Compressor.Supports(cmpr->Algorithm))
                        {
                            try
                            {
                                //Expand a portion of the data
                                byte *buffer = stackalloc byte[CompressBufferLen];
                                Compressor.Expand(cmpr, buffer, CompressBufferLen);

                                //Check for a match
                                if ((n = GetRaw(new DataSource(buffer, CompressBufferLen))) != null)
                                {
                                    //Expand the whole resource and initialize
                                    FileMap map = FileMap.FromTempFile(cmpr->ExpandedSize);
                                    Compressor.Expand(cmpr, map.Address, map.Length);
                                    source.Compression = cmpr->Algorithm;
                                    n.Initialize(parent, source, new DataSource(map));
                                }
                            }
                            catch (InvalidCompressionException e) { MessageBox.Show(e.ToString()); }
                        }
                    }
                }
            }

            return(n);
        }
예제 #5
0
        public void ConvertToV2()
        {
            int    size = 0x08 + Entries.Count * 0x10;
            string path = _workingSource.Map.FilePath;

            _workingSource.Close();
            _workingSource = new DataSource(FileMap.FromTempFile(size));
            VoidPtr addr = _workingSource.Address;

            *(uint *)addr      = 0x0002666f;
            *(int *)(addr + 4) = Entries.Count;
            addr += 0x08;
            for (int i = 0; i < Entries.Count; i++)
            {
                LSEntryObject lsobj = Entries.Values[i];
                LSEntry_v2 *  entry = (LSEntry_v2 *)(addr + (i * 0x10));
                *entry = new LSEntry_v2()
                {
                    _crc     = lsobj.FileNameCRC,
                    _start   = lsobj.DTOffset,
                    _size    = lsobj.Size,
                    _dtIndex = lsobj.DTIndex,
                    _padlen  = lsobj.PaddingLength
                };
            }
            _workingSource.Export(path);
        }
        public void CreateEntry()
        {
            FileMap tempFile = FileMap.FromTempFile(sizeof(ClassicStageBlock));
            // Is this the right way to add a new child node?
            var node = new ClassicStageBlockNode();

            node.Initialize(this, tempFile);
            AddChild(node, true);
        }
예제 #7
0
        /// <summary>
        /// Creates a ResourceNode from a temporary file using FileMap.FromTempFile. The file will be deleted when the underlying FileMap's stream is closed.
        /// </summary>
        public static ResourceNode MakeTempNode(string path)
        {
            byte[] data = File.ReadAllBytes(path);

            FileMap map = FileMap.FromTempFile(data.Length);

            Console.WriteLine(path + " -> FromTempFile -> " + map.FilePath);
            Marshal.Copy(data, 0, map.Address, data.Length);
            return(NodeFactory.FromSource(null, new DataSource(map)));
        }
예제 #8
0
        public unsafe FileMap ToFileMap()
        {
            FileMap map = FileMap.FromTempFile(_data.Length);
            byte *  ptr = (byte *)map.Address;

            for (int i = 0; i < _data.Length; i++)
            {
                ptr[i] = _data[i];
            }
            return(map);
        }
예제 #9
0
        public unsafe virtual void ReplaceRaw(FileMap map)
        {
            if (_children != null)
            {
                foreach (ResourceNode node in _children)
                {
                    node.Dispose();
                }
                _children.Clear();
                _children = null;
            }

            _replUncompSrc.Close();
            _replSrc.Close();

            if (Compressor.IsDataCompressed(map.Address, map.Length))
            {
                CompressionHeader *cmpr = (CompressionHeader *)map.Address;
                _compression = cmpr->Algorithm;
                if (Compressor.Supports(cmpr->Algorithm))
                {
                    FileMap uncompMap = FileMap.FromTempFile(cmpr->ExpandedSize);
                    Compressor.Expand(cmpr, uncompMap.Address, uncompMap.Length);
                    _replSrc       = new DataSource(map, cmpr->Algorithm);
                    _replUncompSrc = new DataSource(uncompMap);
                }
                else
                {
                    _replSrc = _replUncompSrc = new DataSource(map);
                }
            }
            else
            {
                _compression = CompressionType.None;
                _replSrc     = _replUncompSrc = new DataSource(map);
            }

            _replaced = true;
            if (!OnInitialize())
            {
                _children = new List <ResourceNode>();
            }
            _replaced = false;

            _changed = false;
            if (Replaced != null)
            {
                Replaced(this);
            }
        }
예제 #10
0
        /// <summary>
        /// Applies changes.
        /// </summary>
        public void Rebuild()
        {
            FileMap temp = FileMap.FromTempFile(Size);

            // Write changes to the new filemap.
            OnRebuild(temp.Address, temp.Length);

            // Close backing source.
            _replSource.Close();
            // set backing source to new source from temp map.
            _replSource = new DataSource(temp.Address, temp.Length)
            {
                Map = temp
            };
            // Set backing source's map to the temp map.
        }
예제 #11
0
        public virtual FileMap EncodeTPLTexture(Bitmap src, int mipLevels)
        {
            int w = src.Width, h = src.Height;
            int bw = BlockWidth, bh = BlockHeight;

            PixelFormat fmt = src.IsIndexed() ? src.PixelFormat : PixelFormat.Format32bppArgb;

            FileMap fileView = FileMap.FromTempFile(GetFileSize(w, h, mipLevels) + TPLTextureHeader.Size);

            try
            {
                //Build TPL header
                TPLTextureHeader *tex = (TPLTextureHeader *)fileView.Address;
                tex->_wrapS      = 0;
                tex->_wrapT      = 0;
                tex->_minFilter  = 1;
                tex->_magFilter  = 1;
                tex->_minLOD     = 0;
                tex->_maxLOD     = (byte)(mipLevels - 1);
                tex->PixelFormat = RawFormat;
                tex->_width      = (ushort)w;
                tex->_height     = (ushort)h;
                tex->_data       = TPLTextureHeader.Size;

                int     sStep    = bw * Image.GetPixelFormatSize(fmt) / 8;
                int     dStep    = bw * bh * BitsPerPixel / 8;
                VoidPtr baseAddr = fileView.Address;

                using (DIB dib = DIB.FromBitmap(src, bw, bh, fmt))
                {
                    for (int i = 1; i <= mipLevels; i++)
                    {
                        EncodeLevel(baseAddr + tex->_data, dib, src, dStep, sStep, i);
                    }
                }

                return(fileView);
            }
            catch (Exception x)
            {
                MessageBox.Show(x.ToString());
                fileView.Dispose();
                return(null);
            }
        }
예제 #12
0
        public static FileMap EncodePalette(ColorPalette pal, WiiPaletteFormat format)
        {
            FileMap fileView = FileMap.FromTempFile((pal.Entries.Length * 2));

            try
            {
                EncodePalette(fileView.Address, pal, format);
                return(fileView);
            }
            catch (Exception x)
            {
                fileView.Dispose();
                throw;
                //MessageBox.Show(x.ToString());
                //fileView.Dispose();
                //return null;
            }
        }
예제 #13
0
        public static FileMap TryExpand(ref DataSource source, bool doTest = true)
        {
            FileMap         decompressedMap = null;
            CompressionType algorithm       = GetAlgorithm(source);

            if (Supports(source.Compression = algorithm))
            {
                try
                {
                    if (doTest && !Test(algorithm, source.Address))
                    {
                        return(null);
                    }

                    uint len = 0;
                    if (algorithm == CompressionType.RunLengthYAZ0)
                    {
                        len             = *(buint *)(source.Address + 4);
                        decompressedMap = FileMap.FromTempFile((int)len);
                        Expand((YAZ0 *)source.Address, decompressedMap.Address, decompressedMap.Length);
                    }
                    else if (algorithm == CompressionType.RunLengthYAY0)
                    {
                        len             = *(buint *)(source.Address + 4);
                        decompressedMap = FileMap.FromTempFile((int)len);
                        Expand((YAY0 *)source.Address, decompressedMap.Address, decompressedMap.Length);
                    }
                    else
                    {
                        CompressionHeader *hdr = (CompressionHeader *)source.Address;
                        len = hdr->ExpandedSize;

                        decompressedMap = FileMap.FromTempFile((int)len);
                        Expand(hdr, decompressedMap.Address, decompressedMap.Length);
                    }
                }
                catch (InvalidCompressionException e)
                {
                    MessageBox.Show(e.ToString());
                }
            }

            return(decompressedMap);
        }
예제 #14
0
        public static FileMap EncodePLT0Palette(ColorPalette pal, WiiPaletteFormat format)
        {
            FileMap fileView = FileMap.FromTempFile((pal.Entries.Length * 2) + 0x40);

            try
            {
                PLT0v1 *header = (PLT0v1 *)fileView.Address;
                *       header = new PLT0v1(pal.Entries.Length, format);

                EncodePalette(fileView.Address + 0x40, pal, format);
                return(fileView);
            }
            catch (Exception x)
            {
                fileView.Dispose();
                throw;
                //MessageBox.Show(x.ToString());
                //fileView.Dispose();
                //return null;
            }
        }
예제 #15
0
        public static FileMap EncodeTPLPalette(ColorPalette pal, WiiPaletteFormat format)
        {
            FileMap fileView = FileMap.FromTempFile((pal.Entries.Length * 2) + 0xC);

            try
            {
                TPLPaletteHeader *header = (TPLPaletteHeader *)fileView.Address;
                header->_format     = (uint)format;
                header->_numEntries = (ushort)pal.Entries.Length;
                header->_data       = 0xC;

                EncodePalette(fileView.Address + 0xC, pal, format);
                return(fileView);
            }
            catch (Exception x)
            {
                fileView.Dispose();
                throw;
                //MessageBox.Show(x.ToString());
                //fileView.Dispose();
                //return null;
            }
        }
예제 #16
0
        public virtual FileMap EncodeTexture(Bitmap src, int mipLevels)
        {
            int w = src.Width, h = src.Height;
            int bw = BlockWidth, bh = BlockHeight;
            //int aw = w.Align(bw), ah = h.Align(bh);

            PixelFormat fmt = src.IsIndexed() ? src.PixelFormat : PixelFormat.Format32bppArgb;

            //int fileSize = GetMipOffset(w, h, mipLevels + 1) + 0x40;
            FileMap fileView = FileMap.FromTempFile(GetFileSize(w, h, mipLevels, false));

            //FileMap fileView = FileMap.FromTempFile(fileSize);
            try
            {
                //Build TEX header
                TEX0 *header = (TEX0 *)fileView.Address;
                *     header = new TEX0(w, h, RawFormat, mipLevels);

                int     sStep    = bw * Image.GetPixelFormatSize(fmt) / 8;
                int     dStep    = bw * bh * BitsPerPixel / 8;
                VoidPtr baseAddr = header->PixelData;

                using (DIB dib = DIB.FromBitmap(src, bw, bh, fmt))
                    for (int i = 1; i <= mipLevels; i++)
                    {
                        EncodeLevel(header, dib, src, dStep, sStep, i);
                    }

                return(fileView);
            }
            catch (Exception x)
            {
                //MessageBox.Show(x.ToString());
                fileView.Dispose();
                return(null);
            }
        }
예제 #17
0
        public static unsafe ResourceNode FromSource(ResourceNode parent, DataSource source)
        {
            ResourceNode n = null;

            if ((n = GetRaw(source)) != null)
            {
                n.Initialize(parent, source);
            }
            else
            {
                //Check for compression?
                if (Compressor.IsDataCompressed(source.Address, source.Length))
                {
                    CompressionHeader *cmpr = (CompressionHeader *)source.Address;
                    try
                    {
                        //Expand a portion of the data
                        byte *buffer = stackalloc byte[CompressBufferLen];
                        Compressor.Expand(cmpr, buffer, CompressBufferLen);

                        //Check for a match
                        if ((n = GetRaw(new DataSource(buffer, CompressBufferLen))) != null)
                        {
                            //Expand the whole resource and initialize
                            FileMap map = FileMap.FromTempFile(cmpr->ExpandedSize);
                            Compressor.Expand(cmpr, map.Address, map.Length);
                            source.Compression = cmpr->Algorithm;
                            n.Initialize(parent, source, new DataSource(map));
                        }
                    }
                    catch (InvalidCompressionException) { }
                }
            }

            return(n);
        }
예제 #18
0
        public static unsafe FileMap Encode(IAudioStream stream, IProgressTracker progress)
        {
            int    tmp;
            bool   looped   = stream.IsLooping;
            int    channels = stream.Channels;
            int    samples;
            int    blocks;
            int    sampleRate = stream.Frequency;
            int    lbSamples, lbSize, lbTotal;
            int    loopPadding, loopStart, totalSamples;
            short *tPtr;

            if (looped)
            {
                loopStart = stream.LoopStartSample;
                samples   = stream.LoopEndSample; //Set sample size to end sample. That way the audio gets cut off when encoding.

                //If loop point doesn't land on a block, pad the stream so that it does.
                if ((tmp = loopStart % 0x3800) != 0)
                {
                    loopPadding = 0x3800 - tmp;
                    loopStart  += loopPadding;
                }
                else
                {
                    loopPadding = 0;
                }

                totalSamples = loopPadding + samples;
            }
            else
            {
                loopPadding  = loopStart = 0;
                totalSamples = samples = stream.Samples;
            }

            if (progress != null)
            {
                progress.Begin(0, totalSamples * channels * 3, 0);
            }

            blocks = (totalSamples + 0x37FF) / 0x3800;

            //Initialize stream info
            if ((tmp = totalSamples % 0x3800) != 0)
            {
                lbSamples = tmp;
                lbSize    = (lbSamples + 13) / 14 * 8;
                lbTotal   = lbSize.Align(0x20);
            }
            else
            {
                lbSamples = 0x3800;
                lbTotal   = lbSize = 0x2000;
            }

            //Get section sizes
            int rstmSize = 0x40;
            int headSize = (0x68 + (channels * 0x40)).Align(0x20);
            int adpcSize = ((blocks - 1) * 4 * channels + 0x10).Align(0x20);
            int dataSize = ((blocks - 1) * 0x2000 + lbTotal) * channels + 0x20;

            //Create file map
            FileMap map = FileMap.FromTempFile(rstmSize + headSize + adpcSize + dataSize);

            //Get section pointers
            RSTMHeader *    rstm = (RSTMHeader *)map.Address;
            HEADHeader *    head = (HEADHeader *)((int)rstm + rstmSize);
            ADPCHeader *    adpc = (ADPCHeader *)((int)head + headSize);
            RSTMDATAHeader *data = (RSTMDATAHeader *)((int)adpc + adpcSize);

            //Initialize sections
            rstm->Set(headSize, adpcSize, dataSize);
            head->Set(headSize, channels);
            adpc->Set(adpcSize);
            data->Set(dataSize);

            //Set HEAD data
            StrmDataInfo *part1 = head->Part1;

            part1->_format            = new AudioFormatInfo(2, (byte)(looped ? 1 : 0), (byte)channels, 0);
            part1->_sampleRate        = (ushort)sampleRate;
            part1->_blockHeaderOffset = 0;
            part1->_loopStartSample   = loopStart;
            part1->_numSamples        = totalSamples;
            part1->_dataOffset        = rstmSize + headSize + adpcSize + 0x20;
            part1->_numBlocks         = blocks;
            part1->_blockSize         = 0x2000;
            part1->_samplesPerBlock   = 0x3800;
            part1->_lastBlockSize     = lbSize;
            part1->_lastBlockSamples  = lbSamples;
            part1->_lastBlockTotal    = lbTotal;
            part1->_dataInterval      = 0x3800;
            part1->_bitsPerSample     = 4;

            //Create one ADPCMInfo for each channel
            int *       adpcData = stackalloc int[channels];
            ADPCMInfo **pAdpcm   = (ADPCMInfo **)adpcData;

            for (int i = 0; i < channels; i++)
            {
                *(pAdpcm[i] = head->GetChannelInfo(i)) = new ADPCMInfo()
                {
                    _pad = 0
                }
            }
            ;

            //Create buffer for each channel
            int *   bufferData     = stackalloc int[channels];
            short **channelBuffers = (short **)bufferData;
            int     bufferSamples  = totalSamples + 2; //Add two samples for initial yn values

            for (int i = 0; i < channels; i++)
            {
                channelBuffers[i] = tPtr = (short *)Marshal.AllocHGlobal(bufferSamples * 2); //Two bytes per sample

                //Zero padding samples and initial yn values
                for (int x = 0; x < (loopPadding + 2); x++)
                {
                    *tPtr++ = 0;
                }
            }

            //Fill buffers
            stream.SamplePosition = 0;
            short *sampleBuffer = stackalloc short[channels];

            for (int i = 2; i < bufferSamples; i++)
            {
                if (stream.SamplePosition == stream.LoopEndSample && looped)
                {
                    stream.SamplePosition = stream.LoopStartSample;
                }

                stream.ReadSamples(sampleBuffer, 1);
                for (int x = 0; x < channels; x++)
                {
                    channelBuffers[x][i] = sampleBuffer[x];
                }
            }

            //Calculate coefs
            for (int i = 0; i < channels; i++)
            {
                AudioConverter.CalcCoefs(channelBuffers[i] + 2, totalSamples, (short *)pAdpcm[i], progress);
            }

            //Encode blocks
            byte *  dPtr = (byte *)data->Data;
            bshort *pyn  = (bshort *)adpc->Data;

            for (int sIndex = 0, bIndex = 1; sIndex < totalSamples; sIndex += 0x3800, bIndex++)
            {
                int blockSamples = Math.Min(totalSamples - sIndex, 0x3800);
                for (int x = 0; x < channels; x++)
                {
                    short *sPtr = channelBuffers[x] + sIndex;

                    //Set block yn values
                    if (bIndex != blocks)
                    {
                        *pyn++ = sPtr[0x3801];
                        *pyn++ = sPtr[0x3800];
                    }

                    //Encode block (include yn in sPtr)
                    AudioConverter.EncodeBlock(sPtr, blockSamples, dPtr, (short *)pAdpcm[x]);

                    //Set initial ps
                    if (bIndex == 1)
                    {
                        pAdpcm[x]->_ps = *dPtr;
                    }

                    //Advance output pointer
                    if (bIndex == blocks)
                    {
                        //Fill remaining
                        dPtr += lbSize;
                        for (int i = lbSize; i < lbTotal; i++)
                        {
                            *dPtr++ = 0;
                        }
                    }
                    else
                    {
                        dPtr += 0x2000;
                    }
                }

                if (progress != null)
                {
                    if ((sIndex % 0x3800) == 0)
                    {
                        progress.Update(progress.CurrentValue + (0x7000 * channels));
                    }
                }
            }

            //Reverse coefs
            for (int i = 0; i < channels; i++)
            {
                short *p = pAdpcm[i]->_coefs;
                for (int x = 0; x < 16; x++, p++)
                {
                    *p = p->Reverse();
                }
            }

            //Write loop states
            if (looped)
            {
                //Can't we just use block states?
                int loopBlock = loopStart / 0x3800;
                int loopChunk = (loopStart - (loopBlock * 0x3800)) / 14;
                dPtr = (byte *)data->Data + (loopBlock * 0x2000 * channels) + (loopChunk * 8);
                tmp  = (loopBlock == blocks - 1) ? lbTotal : 0x2000;

                for (int i = 0; i < channels; i++, dPtr += tmp)
                {
                    //Use adjusted samples for yn values
                    tPtr             = channelBuffers[i] + loopStart;
                    pAdpcm[i]->_lps  = *dPtr;
                    pAdpcm[i]->_lyn2 = *tPtr++;
                    pAdpcm[i]->_lyn1 = *tPtr;
                }
            }

            //Free memory
            for (int i = 0; i < channels; i++)
            {
                Marshal.FreeHGlobal((IntPtr)channelBuffers[i]);
            }

            if (progress != null)
            {
                progress.Finish();
            }

            return(map);
        }
    }
        public static unsafe FileMap Encode(IAudioStream stream, IProgressTracker progress)
        {
            int  tmp;
            bool looped   = stream.IsLooping;
            int  channels = stream.Channels;
            int  samples;
            int  blocks;
            int  sampleRate = stream.Frequency;
            int  lbSamples, lbSize, lbTotal;
            int /*loopPadding, */ loopStart, totalSamples;
            short *tPtr;

            int blockLen, samplesPerBlock;

            if (looped)
            {
                loopStart = stream.LoopStartSample;
                samples   = stream.LoopEndSample; //Set sample size to end sample. That way the audio gets cut off when encoding.

                blockLen        = (samples.Align(14) / 14 * 8);
                samplesPerBlock = blockLen / 8 * 14;

                //If loop point doesn't land on a block, pad the stream so that it does.
                //if ((tmp = loopStart % samplesPerBlock) != 0)
                //{
                //    loopPadding = samplesPerBlock - tmp;
                //    loopStart += loopPadding;
                //}
                //else
                //    loopPadding = 0;

                totalSamples = /*loopPadding + */ samples;
            }
            else
            {
                //loopPadding = 0;
                loopStart    = 0;
                totalSamples = samples = stream.Samples;

                blockLen        = (samples.Align(14) / 14 * 8);
                samplesPerBlock = blockLen / 8 * 14;
            }

            if (progress != null)
            {
                progress.Begin(0, totalSamples * channels * 3, 0);
            }

            blocks = (totalSamples + (samplesPerBlock - 1)) / samplesPerBlock;

            //Initialize stream info
            if ((tmp = totalSamples % samplesPerBlock) != 0)
            {
                lbSamples = tmp;
                lbSize    = (lbSamples + 13) / 14 * 8;
                lbTotal   = lbSize.Align(0x20);
            }
            else
            {
                lbSamples = samplesPerBlock;
                lbTotal   = lbSize = blockLen;
            }

            //Get section sizes
            int headerSize    = RWAV.Size,
                infoSize      = 8,
                waveSize      = 0x1C,
                tableSize     = channels * 4,
                channelSize   = channels * 0x1C,
                adpcmInfoSize = channels * 0x30,
                entrySize     = (infoSize + waveSize + tableSize + channelSize + adpcmInfoSize).Align(0x20) - 8,
                dataSize      = (((blocks - 1) * blockLen + lbTotal) * channels) + 8;

            //Create file map
            FileMap map = FileMap.FromTempFile(headerSize + entrySize + 8 + dataSize);

            //Get section pointers
            RWAV *header = (RWAV *)map.Address;

            header->_header._tag         = RWAV.Tag;
            header->_header.Endian       = Endian.Big;
            header->_header._version     = 0x102;
            header->_header._length      = map.Length;
            header->_header._firstOffset = 0x20;
            header->_header._numEntries  = 2;

            header->_infoOffset = 0x20;
            header->_infoLength = entrySize + 8;
            header->_dataOffset = 0x20 + entrySize + 8;
            header->_dataLength = dataSize;

            RWAVInfo *infoBlock = header->Info;

            infoBlock->_header._tag    = RWAVInfo.Tag;
            infoBlock->_header._length = entrySize + 8;

            WaveInfo *wave = &infoBlock->_info;

            wave->_format                 = new AudioFormatInfo(2, (byte)(looped ? 1 : 0), (byte)channels, 0);
            wave->_sampleRate             = (ushort)sampleRate;
            wave->_channelInfoTableOffset = 0x1C;
            wave->_dataLocation           = (uint)(header->Data->Data - map.Address);

            wave->LoopSample = loopStart;
            wave->NumSamples = totalSamples;

            RWAVData *dataBlock = header->Data;

            dataBlock->_header._tag    = RWAVData.Tag;
            dataBlock->_header._length = dataSize;

            //Create one ChannelInfo for each channel
            buint *      table       = (buint *)((VoidPtr)wave + 0x1C);
            ChannelInfo *channelInfo = (ChannelInfo *)((VoidPtr)wave + waveSize + tableSize);

            for (int i = 0; i < channels; i++)
            {
                table[i]       = (uint)&channelInfo[i] - (uint)wave;
                channelInfo[i] = new ChannelInfo()
                {
                    _volBackLeft     = 1,
                    _volBackRight    = 1,
                    _volFrontLeft    = 1,
                    _volFrontRight   = 1,
                    _adpcmInfoOffset = waveSize + tableSize + channelSize + i * 0x30
                };
            }

            //Create one ADPCMInfo for each channel
            int *       adpcData = stackalloc int[channels];
            ADPCMInfo **pAdpcm   = (ADPCMInfo **)adpcData;

            for (int i = 0; i < channels; i++)
            {
                *(pAdpcm[i] = wave->GetADPCMInfo(i)) = new ADPCMInfo();
            }

            //Create buffer for each channel
            int *   bufferData     = stackalloc int[channels];
            short **channelBuffers = (short **)bufferData;
            int     bufferSamples  = totalSamples + 2; //Add two samples for initial yn values

            for (int i = 0; i < channels; i++)
            {
                channelBuffers[i] = tPtr = (short *)Marshal.AllocHGlobal(bufferSamples * 2); //Two bytes per sample

                //Zero padding samples and initial yn values
                //for (int x = 0; x < (loopPadding + 2); x++)
                //    *tPtr++ = 0;
            }

            //Fill buffers
            stream.SamplePosition = 0;
            short *sampleBuffer = stackalloc short[channels];

            for (int i = 2; i < bufferSamples; i++)
            {
                //if (stream.SamplePosition == stream.LoopEndSample && looped)
                //    stream.SamplePosition = stream.LoopStartSample;

                stream.ReadSamples(sampleBuffer, 1);
                for (int x = 0; x < channels; x++)
                {
                    channelBuffers[x][i] = sampleBuffer[x];
                }
            }

            //Calculate coefs
            for (int i = 0; i < channels; i++)
            {
                AudioConverter.CalcCoefs(channelBuffers[i] + 2, totalSamples, (short *)pAdpcm[i], progress);
            }

            //Encode blocks
            byte *dPtr = (byte *)dataBlock->Data;

            for (int sIndex = 0, bIndex = 1; sIndex < totalSamples; sIndex += samplesPerBlock, bIndex++)
            {
                int blockSamples = Math.Min(totalSamples - sIndex, samplesPerBlock);
                for (int x = 0; x < channels; x++)
                {
                    channelInfo[x]._channelDataOffset = (int)(dPtr - (byte *)dataBlock->Data);
                    short *sPtr = channelBuffers[x] + sIndex;

                    //Set block yn values
                    if (bIndex != blocks)
                    {
                        pAdpcm[x]->_yn1 = sPtr[samplesPerBlock + 1];
                        pAdpcm[x]->_yn2 = sPtr[samplesPerBlock];
                    }

                    //Encode block (include yn in sPtr)
                    AudioConverter.EncodeBlock(sPtr, blockSamples, dPtr, (short *)pAdpcm[x]);

                    //Set initial ps
                    if (bIndex == 1)
                    {
                        pAdpcm[x]->_ps = *dPtr;
                    }

                    //Advance output pointer
                    if (bIndex == blocks)
                    {
                        //Fill remaining
                        dPtr += lbSize;
                        for (int i = lbSize; i < lbTotal; i++)
                        {
                            *dPtr++ = 0;
                        }
                    }
                    else
                    {
                        dPtr += blockLen;
                    }
                }

                if (progress != null && (sIndex % samplesPerBlock) == 0)
                {
                    progress.Update(progress.CurrentValue + (samplesPerBlock * 2 * channels));
                }
            }

            //Reverse coefs
            for (int i = 0; i < channels; i++)
            {
                short *p = pAdpcm[i]->_coefs;
                for (int x = 0; x < 16; x++, p++)
                {
                    *p = p->Reverse();
                }
            }

            //Write loop states
            if (looped)
            {
                //Can't we just use block states?
                int loopBlock = loopStart / samplesPerBlock;
                int loopChunk = (loopStart - (loopBlock * samplesPerBlock)) / 14;
                dPtr = (byte *)dataBlock->Data + (loopBlock * blockLen * channels) + (loopChunk * 8);
                tmp  = (loopBlock == blocks - 1) ? lbTotal : blockLen;

                for (int i = 0; i < channels; i++, dPtr += tmp)
                {
                    //Use adjusted samples for yn values
                    tPtr             = channelBuffers[i] + loopStart;
                    pAdpcm[i]->_lps  = *dPtr;
                    pAdpcm[i]->_lyn2 = *tPtr++;
                    pAdpcm[i]->_lyn1 = *tPtr;
                }
            }

            //Free memory
            for (int i = 0; i < channels; i++)
            {
                Marshal.FreeHGlobal((IntPtr)channelBuffers[i]);
            }

            if (progress != null)
            {
                progress.Finish();
            }

            return(map);
        }
예제 #20
0
        //Parser commands must initialize the node before returning.
        public unsafe static ResourceNode FromFile(ResourceNode parent, string path)
        {
            ResourceNode node = null;
            FileMap      map  = FileMap.FromFile(path, FileMapProtect.Read);

            try
            {
                DataSource source = new DataSource(map);
                if (String.Equals(Path.GetExtension(path), ".mrg", StringComparison.OrdinalIgnoreCase) || String.Equals(Path.GetExtension(path), ".mrgc", StringComparison.OrdinalIgnoreCase))
                {
                    node = new MRGNode();
                    if (Compressor.IsDataCompressed(source.Address, source.Length))
                    {
                        CompressionHeader *cmpr = (CompressionHeader *)source.Address;
                        source.Compression = cmpr->Algorithm;
                        if (Compressor.Supports(cmpr->Algorithm))
                        {
                            try
                            {
                                //Expand the whole resource and initialize
                                FileMap uncompMap = FileMap.FromTempFile(cmpr->ExpandedSize);
                                Compressor.Expand(cmpr, uncompMap.Address, uncompMap.Length);
                                node.Initialize(parent, source, new DataSource(uncompMap));
                            }
                            catch (InvalidCompressionException e) { MessageBox.Show(e.ToString()); }
                        }
                        else
                        {
                            node.Initialize(parent, source);
                        }
                    }
                    else
                    {
                        node.Initialize(parent, source);
                    }
                }
                else if (String.Equals(Path.GetExtension(path), ".rel", StringComparison.OrdinalIgnoreCase))
                {
                    node = new RELNode();
                    node.Initialize(parent, map);
                }
                else if (String.Equals(Path.GetExtension(path), ".dol", StringComparison.OrdinalIgnoreCase))
                {
                    node = new DOLNode();
                    node.Initialize(parent, map);
                }
                else if ((node = FromSource(parent, source)) == null)
                {
                    //if (Compressor.IsDataCompressed(source.Address, source.Length))
                    //{
                    //    CompressionHeader* cmpr = (CompressionHeader*)source.Address;
                    //    if (!Compressor.Supports(cmpr->Algorithm))
                    //        MessageBox.Show("File uses unsupported " + cmpr->Algorithm.ToString() + " compression.");
                    //}
                }
            }
            finally { if (node == null)
                      {
                          map.Dispose();
                      }
            }
            return(node);
        }
예제 #21
0
        public virtual FileMap EncodeREFTTexture(Bitmap src, int mipLevels, WiiPaletteFormat format, bool usePalette)
        {
            int w = src.Width, h = src.Height;
            int bw = BlockWidth, bh = BlockHeight;
            //int aw = w.Align(bw), ah = h.Align(bh);
            ColorPalette pal = src.Palette;

            PixelFormat fmt = src.IsIndexed() ? src.PixelFormat : PixelFormat.Format32bppArgb;

            //int fileSize = GetMipOffset(w, h, mipLevels + 1) + 0x20;
            FileMap fileView = FileMap.FromTempFile(GetFileSize(w, h, mipLevels, true) + (usePalette ? (pal.Entries.Length * 2) : 0));

            //FileMap fileView = FileMap.FromTempFile(fileSize);
            try
            {
                //Build REFT image header
                REFTData *header = (REFTData *)fileView.Address;
                *         header = new REFTData((ushort)w, (ushort)h, (byte)RawFormat);
                header->_imagelen = (uint)fileView.Length - 0x20;

                int     sStep    = bw * Image.GetPixelFormatSize(fmt) / 8;
                int     dStep    = bw * bh * BitsPerPixel / 8;
                VoidPtr baseAddr = (byte *)header + 0x20;

                using (DIB dib = DIB.FromBitmap(src, bw, bh, fmt))
                    for (int i = 1; i <= mipLevels; i++)
                    {
                        EncodeLevel(baseAddr, dib, src, dStep, sStep, i);
                    }

                if (usePalette)
                {
                    int count = pal.Entries.Length;

                    header->_colorCount = (ushort)count;
                    header->_pltFormat  = (byte)format;

                    switch (format)
                    {
                    case WiiPaletteFormat.IA8:
                    {
                        IA8Pixel *dPtr = (IA8Pixel *)header->PaletteData;
                        for (int i = 0; i < count; i++)
                        {
                            dPtr[i] = (IA8Pixel)pal.Entries[i];
                        }
                        break;
                    }

                    case WiiPaletteFormat.RGB565:
                    {
                        wRGB565Pixel *dPtr = (wRGB565Pixel *)header->PaletteData;
                        for (int i = 0; i < count; i++)
                        {
                            dPtr[i] = (wRGB565Pixel)pal.Entries[i];
                        }
                        break;
                    }

                    case WiiPaletteFormat.RGB5A3:
                    {
                        wRGB5A3Pixel *dPtr = (wRGB5A3Pixel *)header->PaletteData;
                        for (int i = 0; i < count; i++)
                        {
                            dPtr[i] = (wRGB5A3Pixel)pal.Entries[i];
                        }
                        break;
                    }
                    }
                }

                return(fileView);
            }
            catch (Exception x)
            {
                //MessageBox.Show(x.ToString());
                fileView.Dispose();
                return(null);
            }
        }
예제 #22
0
        public static unsafe FileMap Encode(IAudioStream stream, IProgressTracker progress, WaveEncoding encoding = WaveEncoding.ADPCM)
#endif
        {
            int    tmp;
            bool   looped   = stream.IsLooping;
            int    channels = stream.Channels;
            int    samples;
            int    blocks;
            int    sampleRate = stream.Frequency;
            int    lbSamples, lbSize, lbTotal;
            int    loopPadding, loopStart, totalSamples;
            short *tPtr;

            int samplesPerBlock = encoding == WaveEncoding.ADPCM ? 0x3800
                : encoding == WaveEncoding.PCM16 ? 0x1000
                : 0;

            if (samplesPerBlock == 0)
            {
                throw new ArgumentException("Encoding must be ADPCM or PCM16");
            }

            if (looped)
            {
                loopStart = stream.LoopStartSample;
                samples   = stream.LoopEndSample; //Set sample size to end sample. That way the audio gets cut off when encoding.

                //If loop point doesn't land on a block, pad the stream so that it does.
                if ((tmp = loopStart % samplesPerBlock) != 0)
                {
                    loopPadding = samplesPerBlock - tmp;
                    loopStart  += loopPadding;
                }
                else
                {
                    loopPadding = 0;
                }

                totalSamples = loopPadding + samples;
            }
            else
            {
                loopPadding  = loopStart = 0;
                totalSamples = samples = stream.Samples;
            }

            if (progress != null)
            {
                progress.Begin(0, totalSamples * channels * 3, 0);
            }

            blocks = (totalSamples + samplesPerBlock - 1) / samplesPerBlock;

            //Initialize stream info
            if ((tmp = totalSamples % samplesPerBlock) != 0)
            {
                lbSamples = tmp;
                if (encoding == WaveEncoding.ADPCM)
                {
                    lbSize = (lbSamples + 13) / 14 * 8;
                }
                else if (encoding == WaveEncoding.PCM16)
                {
                    lbTotal = lbSize = lbSamples * 2;
                }
                else if (encoding == WaveEncoding.PCM8)
                {
                    lbTotal = lbSize = lbSamples;
                }
                else
                {
                    throw new NotImplementedException();
                }
                lbTotal = lbSize.Align(0x20);
            }
            else
            {
                lbSamples = samplesPerBlock;
                lbTotal   = lbSize = 0x2000;
            }

            //Get section sizes
            int rstmSize = 0x40;
            int headSize = (0x68 + (channels * (encoding == WaveEncoding.ADPCM ? 0x40 : 0x10))).Align(0x20);
            int adpcSize = encoding == WaveEncoding.ADPCM
                ? ((blocks - 1) * 4 * channels + 0x10).Align(0x20)
                : 0;
            int dataSize = ((blocks - 1) * 0x2000 + lbTotal) * channels + 0x20;

#if RSTMLIB
            //Create byte array
            byte[] array = new byte[rstmSize + headSize + adpcSize + dataSize];
            fixed(byte *address = array)
            {
#else
            //Create file map
            FileMap map     = FileMap.FromTempFile(rstmSize + headSize + adpcSize + dataSize);
            VoidPtr address = map.Address;
#endif

                //Get section pointers
                RSTMHeader *    rstm = (RSTMHeader *)address;
                HEADHeader *    head = (HEADHeader *)((byte *)rstm + rstmSize);
                ADPCHeader *    adpc = (ADPCHeader *)((byte *)head + headSize);
                RSTMDATAHeader *data = (RSTMDATAHeader *)((byte *)adpc + adpcSize);

                //Initialize sections
                rstm->Set(headSize, adpcSize, dataSize);
                head->Set(headSize, channels, encoding);
                if (adpcSize > 0)
                {
                    adpc->Set(adpcSize);
                }
                data->Set(dataSize);

                //Set HEAD data
                StrmDataInfo *part1 = head->Part1;
                part1->_format            = new AudioFormatInfo((byte)encoding, (byte)(looped ? 1 : 0), (byte)channels, 0);
                part1->_sampleRate        = (ushort)sampleRate;
                part1->_blockHeaderOffset = 0;
                part1->_loopStartSample   = loopStart;
                part1->_numSamples        = totalSamples;
                part1->_dataOffset        = rstmSize + headSize + adpcSize + 0x20;
                part1->_numBlocks         = blocks;
                part1->_blockSize         = 0x2000;
                part1->_samplesPerBlock   = samplesPerBlock;
                part1->_lastBlockSize     = lbSize;
                part1->_lastBlockSamples  = lbSamples;
                part1->_lastBlockTotal    = lbTotal;
                part1->_dataInterval      = encoding == WaveEncoding.ADPCM ? samplesPerBlock : 0;
                part1->_bitsPerSample     = encoding == WaveEncoding.ADPCM ? 4 : 0;

                if (encoding == WaveEncoding.ADPCM)
                {
                    //Create one ADPCMInfo for each channel
                    int *       adpcData = stackalloc int[channels];
                    ADPCMInfo **pAdpcm   = (ADPCMInfo **)adpcData;
                    for (int i = 0; i < channels; i++)
                    {
                        *(pAdpcm[i] = head->GetChannelInfo(i)) = new ADPCMInfo()
                        {
                            _pad = 0
                        }
                    }
                    ;

                    //Create buffer for each channel
                    int *   bufferData     = stackalloc int[channels];
                    short **channelBuffers = (short **)bufferData;
                    int     bufferSamples  = totalSamples + 2; //Add two samples for initial yn values
                    for (int i = 0; i < channels; i++)
                    {
                        channelBuffers[i] = tPtr = (short *)Marshal.AllocHGlobal(bufferSamples * 2); //Two bytes per sample

                        //Zero padding samples and initial yn values
                        for (int x = 0; x < (loopPadding + 2); x++)
                        {
                            *tPtr++ = 0;
                        }
                    }

                    //Fill buffers
                    stream.SamplePosition = 0;
                    short *sampleBuffer = stackalloc short[channels];

                    for (int i = 2; i < bufferSamples; i++)
                    {
                        if (stream.SamplePosition == stream.LoopEndSample && looped)
                        {
                            stream.SamplePosition = stream.LoopStartSample;
                        }

                        stream.ReadSamples(sampleBuffer, 1);
                        for (int x = 0; x < channels; x++)
                        {
                            channelBuffers[x][i] = sampleBuffer[x];
                        }
                    }

                    //Calculate coefs
                    for (int i = 0; i < channels; i++)
                    {
                        AudioConverter.CalcCoefs(channelBuffers[i] + 2, totalSamples, (short *)pAdpcm[i], progress);
                    }

                    //Encode blocks
                    byte *  dPtr = (byte *)data->Data;
                    bshort *pyn  = (bshort *)adpc->Data;
                    for (int x = 0; x < channels; x++)
                    {
                        *pyn++ = 0;
                        *pyn++ = 0;
                    }

                    for (int sIndex = 0, bIndex = 1; sIndex < totalSamples; sIndex += samplesPerBlock, bIndex++)
                    {
                        int blockSamples = Math.Min(totalSamples - sIndex, samplesPerBlock);
                        for (int x = 0; x < channels; x++)
                        {
                            short *sPtr = channelBuffers[x] + sIndex;

                            //Set block yn values
                            if (bIndex != blocks)
                            {
                                *pyn++ = sPtr[samplesPerBlock + 1];
                                *pyn++ = sPtr[samplesPerBlock];
                            }

                            //Encode block (include yn in sPtr)
                            AudioConverter.EncodeBlock(sPtr, blockSamples, dPtr, (short *)pAdpcm[x]);

                            //Set initial ps
                            if (bIndex == 1)
                            {
                                pAdpcm[x]->_ps = *dPtr;
                            }

                            //Advance output pointer
                            if (bIndex == blocks)
                            {
                                //Fill remaining
                                dPtr += lbSize;
                                for (int i = lbSize; i < lbTotal; i++)
                                {
                                    *dPtr++ = 0;
                                }
                            }
                            else
                            {
                                dPtr += 0x2000;
                            }
                        }

                        if (progress != null)
                        {
                            if ((sIndex % samplesPerBlock) == 0)
                            {
                                progress.Update(progress.CurrentValue + (0x7000 * channels));
                            }
                        }
                    }

                    //Reverse coefs
                    for (int i = 0; i < channels; i++)
                    {
                        short *p = pAdpcm[i]->_coefs;
                        for (int x = 0; x < 16; x++, p++)
                        {
                            *p = p->Reverse();
                        }
                    }

                    //Write loop states
                    if (looped)
                    {
                        //Can't we just use block states?
                        int loopBlock = loopStart / samplesPerBlock;
                        int loopChunk = (loopStart - (loopBlock * samplesPerBlock)) / 14;
                        dPtr = (byte *)data->Data + (loopBlock * 0x2000 * channels) + (loopChunk * 8);
                        tmp  = (loopBlock == blocks - 1) ? lbTotal : 0x2000;

                        for (int i = 0; i < channels; i++, dPtr += tmp)
                        {
                            //Use adjusted samples for yn values
                            tPtr             = channelBuffers[i] + loopStart;
                            pAdpcm[i]->_lps  = *dPtr;
                            pAdpcm[i]->_lyn2 = *tPtr++;
                            pAdpcm[i]->_lyn1 = *tPtr;
                        }
                    }

                    //Free memory
                    for (int i = 0; i < channels; i++)
                    {
                        Marshal.FreeHGlobal((IntPtr)channelBuffers[i]);
                    }
                }
                else if (encoding == WaveEncoding.PCM16)
                {
                    bshort *destPtr = (bshort *)data->Data;
                    for (int i = 0; i < blocks; i++)
                    {
                        int samplesPerChannel = i < blocks - 1
                        ? part1->_samplesPerBlock
                        : part1->_lastBlockSamples;
                        int bytesPerChannel = i < blocks - 1
                        ? part1->_blockSize
                        : part1->_lastBlockTotal;
                        short[] sampleData = new short[channels * bytesPerChannel / sizeof(short)];

                        fixed(short *sampleDataPtr = sampleData)
                        {
                            int read = 0;

                            do
                            {
                                if (stream.SamplePosition == stream.LoopEndSample && looped)
                                {
                                    stream.SamplePosition = stream.LoopStartSample;
                                }
                                int s = stream.ReadSamples(sampleDataPtr + read, samplesPerChannel - read);
                                if (s == 0)
                                {
                                    throw new Exception("No samples could be read from the stream");
                                }
                                read += s;
                            }while (read < samplesPerChannel);
                        }

                        for (int j = 0; j < channels; j++)
                        {
                            for (int k = j; k < sampleData.Length; k += channels)
                            {
                                *(destPtr++) = sampleData[k];
                            }
                        }

                        progress.Update(progress.CurrentValue + (samplesPerChannel * channels * 3));
                    }
                }

                if (progress != null)
                {
                    progress.Finish();
                }

#if RSTMLIB
            }

            return(array);
#else
                return(map);
#endif
        }
예제 #23
0
        public virtual FileMap EncodeREFTTexture(Bitmap src, int mipLevels, WiiPaletteFormat format)
        {
            int w = src.Width, h = src.Height;
            int bw = BlockWidth, bh = BlockHeight;

            ColorPalette pal = src.Palette;

            PixelFormat fmt = src.IsIndexed() ? src.PixelFormat : PixelFormat.Format32bppArgb;

            FileMap fileView = FileMap.FromTempFile(GetFileSize(w, h, mipLevels) + 0x20 + (pal != null ? (pal.Entries.Length * 2) : 0));

            try
            {
                //Build REFT image header
                REFTImageHeader *header = (REFTImageHeader *)fileView.Address;
                *header = new REFTImageHeader((ushort)w, (ushort)h, (byte)RawFormat, (byte)format, (ushort)(pal != null ? pal.Entries.Length : 0), (uint)fileView.Length - 0x20 - (uint)(pal != null ? (pal.Entries.Length * 2) : 0), (byte)(mipLevels - 1));

                int sStep = bw * Image.GetPixelFormatSize(fmt) / 8;
                int dStep = bw * bh * BitsPerPixel / 8;

                using (DIB dib = DIB.FromBitmap(src, bw, bh, fmt))
                    for (int i = 1; i <= mipLevels; i++)
                    {
                        EncodeLevel((VoidPtr)header + 0x20, dib, src, dStep, sStep, i);
                    }

                if (pal != null)
                {
                    int count = pal.Entries.Length;

                    switch (format)
                    {
                    case WiiPaletteFormat.IA8:
                    {
                        IA8Pixel *dPtr = (IA8Pixel *)header->PaletteData;
                        for (int i = 0; i < count; i++)
                        {
                            dPtr[i] = (IA8Pixel)pal.Entries[i];
                        }
                        break;
                    }

                    case WiiPaletteFormat.RGB565:
                    {
                        wRGB565Pixel *dPtr = (wRGB565Pixel *)header->PaletteData;
                        for (int i = 0; i < count; i++)
                        {
                            dPtr[i] = (wRGB565Pixel)pal.Entries[i];
                        }
                        break;
                    }

                    case WiiPaletteFormat.RGB5A3:
                    {
                        wRGB5A3Pixel *dPtr = (wRGB5A3Pixel *)header->PaletteData;
                        for (int i = 0; i < count; i++)
                        {
                            dPtr[i] = (wRGB5A3Pixel)pal.Entries[i];
                        }
                        break;
                    }
                    }
                }

                return(fileView);
            }
            catch (Exception x)
            {
                MessageBox.Show(x.ToString());
                fileView.Dispose();
                return(null);
            }
        }