コード例 #1
0
    public static FlicChunk Load(ISerializer s, int width, int height)
    {
        if (s == null)
        {
            throw new ArgumentNullException(nameof(s));
        }

        var  chunkSizeOffset = s.Offset;
        uint chunkSize       = s.UInt32(null, 0);

        if ((chunkSize & 0x1) != 0)
        {
            chunkSize++;
        }
        FlicChunkType type = (FlicChunkType)s.UInt16(null, 0);

        // Chunk
        FlicChunk c = type switch
        {
            FlicChunkType.Palette8Bit => new Palette8Chunk(),
            FlicChunkType.DeltaWordOrientedRle => new DeltaFlcChunk(),
            FlicChunkType.FullByteOrientedRle => new FullByteOrientedRleChunk(width, height),
            FlicChunkType.FullUncompressed => new CopyChunk(),
            FlicChunkType.Frame => new FlicFrame(width, height),
            // FlicChunkType.Palette6Bit          => new Palette6Chunk(),
            // FlicChunkType.DeltaByteOrientedRle => new DeltaFliChunk(),
            // FlicChunkType.BlackFrameData       => new BlackFrameChunk(),
            // FlicChunkType.Thumbnail            => new ThumbnailChunk(),
            _ => new UnknownChunk(type)
        };

        // Fix export issue in Autodesk Animator
        if (type == FlicChunkType.FullUncompressed &&
            width * height + ChunkHeaderSize - 2 == chunkSize)
        {
            chunkSize += 2;
        }

        chunkSize = c.LoadChunk(chunkSize - ChunkHeaderSize, s) + ChunkHeaderSize;

        var actualChunkSize = s.Offset - chunkSizeOffset;

        if (actualChunkSize - chunkSize < 4) // pad
        {
            for (long i = chunkSize - actualChunkSize; i != 0; i--)
            {
                s.UInt8(null, 0);
            }

            actualChunkSize = s.Offset - chunkSizeOffset;
        }

        ApiUtil.Assert(actualChunkSize == chunkSize);
        return(c);
    }
}
コード例 #2
0
    public FlicFile(ISerializer s)
    {
        if (s == null)
        {
            throw new ArgumentNullException(nameof(s));
        }
        if (s.IsWriting())
        {
            throw new NotImplementedException("FLIC file writing not currently supported");
        }

        long startOffset = s.Offset;

        Size        = s.UInt32(null, 0);                 // Size of FLIC including this header
        Type        = (FlicHeaderType)s.UInt16(null, 0); // File type 0xAF11, 0xAF12, 0xAF30, 0xAF44, ...
        Frames      = s.UInt16(null, 0);                 // Number of frames in first segment
        Width       = s.UInt16(null, 0);                 // FLIC width in pixels
        Height      = s.UInt16(null, 0);                 // FLIC height in pixels
        Depth       = s.UInt16(null, 0);                 // Bits per pixel (usually 8)
        Flags       = s.UInt16(null, 0);                 // Set to zero or to three
        Speed       = s.UInt32(null, 0);                 // Delay between frames in jiffies (1/70 s)
        Reserved1   = s.UInt16(null, 0);                 // Set to zero
        Created     = s.UInt32(null, 0);                 // Date of FLIC creation (FLC only)
        Creator     = s.UInt32(null, 0);                 // Serial number or compiler id (FLC only)
        Updated     = s.UInt32(null, 0);                 // Date of FLIC update (FLC only)
        Updater     = s.UInt32(null, 0);                 // Serial number (FLC only), see creator
        AspectDx    = s.UInt16(null, 0);                 // Width of square rectangle (FLC only)
        AspectDy    = s.UInt16(null, 0);                 // Height of square rectangle (FLC only)
        ExtFlags    = s.UInt16(null, 0);                 // EGI: flags for specific EGI extensions
        KeyFrames   = s.UInt16(null, 0);                 // EGI: key-image frequency
        TotalFrames = s.UInt16(null, 0);                 // EGI: total number of frames (segments)
        ReqMemory   = s.UInt32(null, 0);                 // EGI: maximum chunk size (uncompressed)
        MaxRegions  = s.UInt16(null, 0);                 // EGI: max. number of regions in a CHK_REGION chunk
        TranspNum   = s.UInt16(null, 0);                 // EGI: number of transparent levels
        Reserved2   = s.Bytes(null, null, 24);           // Set to zero
        OFrame1     = s.UInt32(null, 0);                 // Offset to frame 1 (FLC only)
        OFrame2     = s.UInt32(null, 0);                 // Offset to frame 2 (FLC only)
        Reserved3   = s.Bytes(null, null, 40);           // Set to zero

        var finalOffset = startOffset + Size;

        while (s.Offset < finalOffset)
        {
            Chunks.Add(FlicChunk.Load(s, Width, Height));
        }
    }