Пример #1
0
        private void SerializeCompressedData(FAssetArchive Ar)
        {
            // These fields were serialized as properties in pre-UE4.12 engine version
            KeyEncodingFormat            = Ar.Read <AnimationKeyFormat>();
            TranslationCompressionFormat = Ar.Read <AnimationCompressionFormat>();
            RotationCompressionFormat    = Ar.Read <AnimationCompressionFormat>();
            ScaleCompressionFormat       = Ar.Read <AnimationCompressionFormat>();

            CompressedTrackOffsets = Ar.ReadArray <int>();
            CompressedScaleOffsets = new FCompressedOffsetData(Ar);

            if (Ar.Game >= EGame.GAME_UE4_21)
            {
                // UE4.21+ - added compressed segments; disappeared in 4.23
                CompressedSegments = Ar.ReadArray <FCompressedSegment>();
                if (CompressedSegments.Length > 0)
                {
                    Log.Information("animation has CompressedSegments!");
                }
            }

            CompressedTrackToSkeletonMapTable = Ar.ReadArray <FTrackToSkeletonMap>();

            if (Ar.Game < EGame.GAME_UE4_22)
            {
                CompressedCurveData = new FStructFallback(Ar, "RawCurveTracks");
            }
            else
            {
                var compressedCurveNames = Ar.ReadArray(() => new FSmartName(Ar));
            }

            if (Ar.Game >= EGame.GAME_UE4_17)
            {
                // UE4.17+
                var compressedRawDataSize = Ar.Read <int>();
            }

            if (Ar.Game >= EGame.GAME_UE4_22)
            {
                var compressedNumFrames = Ar.Read <int>();
            }

            // compressed data
            var numBytes = Ar.Read <int>();

            CompressedByteStream = Ar.ReadBytes(numBytes);

            if (Ar.Game >= EGame.GAME_UE4_22)
            {
                var curveCodecPath            = Ar.ReadFString();
                var compressedCurveByteStream = Ar.ReadArray <byte>();
            }

            // Fix layout of "byte swapped" data (workaround for UE4 bug)
            if (KeyEncodingFormat == AnimationKeyFormat.AKF_PerTrackCompression && CompressedScaleOffsets.OffsetData.Length > 0 && Ar.Game < EGame.GAME_UE4_23)
            {
                throw new NotImplementedException();
            }
        }
Пример #2
0
        // UE4.23-4.24 has changed compressed data layout for streaming, so it's worth making a separate
        // serializer function for it.
        private void SerializeCompressedData2(FAssetArchive Ar)
        {
            var compressedRawDataSize = Ar.Read <int>();

            CompressedTrackToSkeletonMapTable = Ar.ReadArray <FTrackToSkeletonMap>();
            var compressedCurveNames = Ar.ReadArray(() => new FSmartName(Ar));

            // Since 4.23, this is FUECompressedAnimData::SerializeCompressedData
            KeyEncodingFormat            = Ar.Read <AnimationKeyFormat>();
            TranslationCompressionFormat = Ar.Read <AnimationCompressionFormat>();
            RotationCompressionFormat    = Ar.Read <AnimationCompressionFormat>();
            ScaleCompressionFormat       = Ar.Read <AnimationCompressionFormat>();

            var compressedNumFrames = Ar.Read <int>();

            // SerializeView() just serializes array size
            var compressedTrackOffsetsNum = Ar.Read <int>();
            var compressedScaleOffsetsNum = Ar.Read <int>();

            CompressedScaleOffsets = new FCompressedOffsetData(Ar.Read <int>());
            var compressedByteStreamNum = Ar.Read <int>();
            // ... end of FUECompressedAnimData::SerializeCompressedData

            var numBytes            = Ar.Read <int>();
            var bUseBulkDataForLoad = Ar.ReadBoolean();

            // In UE4.23 CompressedByteStream field exists in FUECompressedAnimData (as TArrayView) and in
            // FCompressedAnimSequence (as byte array). Serialization is done in FCompressedAnimSequence,
            // either as TArray or as bulk, and then array is separated onto multiple "views" for
            // FUECompressedAnimData. We'll use a different name for "joined" serialized array here to
            // avoid confuse.
            byte[] serializedByteStream;

            if (bUseBulkDataForLoad)
            {
                throw new NotImplementedException("Anim: bUseBulkDataForLoad not implemented");
                //todo: read from bulk to serializedByteStream
            }
            else
            {
                serializedByteStream = Ar.ReadBytes(numBytes);
            }

            // Setup all array views from single array. In UE4 this is done in FUECompressedAnimData::InitViewsFromBuffer.
            // We'll simply copy array data away from SerializedByteStream, and then SerializedByteStream
            // will be released from memory as it is a local variable here.
            // Note: copying is not byte-order wise, so if there will be any problems in the future,
            // should use byte swap functions.
            using (var tempAr = new FByteArchive("SerializedByteStream", serializedByteStream, Ar.Versions))
            {
                CompressedTrackOffsets            = tempAr.ReadArray <int>(compressedTrackOffsetsNum);
                CompressedScaleOffsets.OffsetData = tempAr.ReadArray <int>(compressedScaleOffsetsNum);
                CompressedByteStream = tempAr.ReadBytes(compressedByteStreamNum);
            }

            var curveCodecPath            = Ar.ReadFString();
            var compressedCurveByteStream = Ar.ReadArray <byte>();
        }