diff --git a/Source/Engine/Content/Assets/MaterialInstance.cpp b/Source/Engine/Content/Assets/MaterialInstance.cpp index ca9e793b3..537fe0243 100644 --- a/Source/Engine/Content/Assets/MaterialInstance.cpp +++ b/Source/Engine/Content/Assets/MaterialInstance.cpp @@ -8,6 +8,9 @@ #include "Engine/Content/Factories/BinaryAssetFactory.h" #include "Engine/Serialization/MemoryReadStream.h" #include "Engine/Threading/Threading.h" +#if USE_EDITOR +#include "Engine/Serialization/MemoryWriteStream.h" +#endif REGISTER_BINARY_ASSET_WITH_UPGRADER(MaterialInstance, "FlaxEngine.MaterialInstance", MaterialInstanceUpgrader, true); diff --git a/Source/Engine/Content/Assets/Model.cpp b/Source/Engine/Content/Assets/Model.cpp index 8ba26658c..52f633e1b 100644 --- a/Source/Engine/Content/Assets/Model.cpp +++ b/Source/Engine/Content/Assets/Model.cpp @@ -23,6 +23,9 @@ #include "Engine/Renderer/DrawCall.h" #include "Engine/Threading/Threading.h" #include "Engine/Tools/ModelTool/ModelTool.h" +#if USE_EDITOR +#include "Engine/Serialization/MemoryWriteStream.h" +#endif REGISTER_BINARY_ASSET_ABSTRACT(ModelBase, "FlaxEngine.ModelBase"); @@ -456,6 +459,7 @@ bool Model::Save(bool withMeshDataFromGpu, const StringView& path) return true; } + // #MODEL_DATA_FORMAT_USAGE meshesStream.WriteUint32(vertices); meshesStream.WriteUint32(triangles); diff --git a/Source/Engine/Content/Assets/SkinnedModel.cpp b/Source/Engine/Content/Assets/SkinnedModel.cpp index 0b9c69275..933643f63 100644 --- a/Source/Engine/Content/Assets/SkinnedModel.cpp +++ b/Source/Engine/Content/Assets/SkinnedModel.cpp @@ -19,6 +19,9 @@ #include "Engine/Graphics/Models/MeshDeformation.h" #include "Engine/Profiler/ProfilerCPU.h" #include "Engine/Renderer/DrawCall.h" +#if USE_EDITOR +#include "Engine/Serialization/MemoryWriteStream.h" +#endif REGISTER_BINARY_ASSET_WITH_UPGRADER(SkinnedModel, "FlaxEngine.SkinnedModel", SkinnedModelAssetUpgrader, true); diff --git a/Source/Engine/Content/Upgraders/AudioClipUpgrader.h b/Source/Engine/Content/Upgraders/AudioClipUpgrader.h index 98d3e3e68..cf1e2594a 100644 --- a/Source/Engine/Content/Upgraders/AudioClipUpgrader.h +++ b/Source/Engine/Content/Upgraders/AudioClipUpgrader.h @@ -5,9 +5,6 @@ #if USE_EDITOR #include "BinaryAssetUpgrader.h" -#include "Engine/Audio/AudioClip.h" -#include "Engine/Tools/AudioTool/OggVorbisDecoder.h" -#include "Engine/Serialization/MemoryReadStream.h" /// /// Audio Clip asset upgrader. @@ -23,112 +20,12 @@ public: { static const Upgrader upgraders[] = { - { 1, 2, &Upgrade_1_To_2 }, + {}, }; setup(upgraders, ARRAY_COUNT(upgraders)); } private: - // ============================================ - // Version 1: - // Designed: 26.02.2018 - // Header version 1. - // Chunks with audio data. - // ============================================ - // Version 2: - // Designed: 08.08.2019 - // Header version 2. - // Chunks with audio data. - // ============================================ - - /// - /// Audio Clip resource header structure, version 1. Added on 26.02.2018. - /// [Deprecated on 08/08/2019, expires on 08/09/2020] - /// - struct Header1 - { - AudioFormat Format; - AudioDataInfo Info; - bool Is3D; - bool Streamable; - uint32 OriginalSize; - uint32 ImportedSize; - }; - - typedef AudioClip::Header Header2; - - static bool Upgrade_1_To_2(AssetMigrationContext& context) - { - ASSERT(context.Input.SerializedVersion == 1 && context.Output.SerializedVersion == 2); - - // Copy all chunks - if (CopyChunks(context)) - return true; - - // Convert header - if (context.Input.CustomData.IsInvalid()) - return true; - auto& oldHeader = *(Header1*)context.Input.CustomData.Get(); - Header2 newHeader; - newHeader.Format = oldHeader.Format; - newHeader.Info = oldHeader.Info; - newHeader.Is3D = oldHeader.Is3D; - newHeader.Streamable = oldHeader.Streamable; - newHeader.OriginalSize = oldHeader.OriginalSize; - newHeader.ImportedSize = oldHeader.ImportedSize; - Platform::MemoryClear(newHeader.SamplesPerChunk, sizeof(newHeader.SamplesPerChunk)); - for (int32 chunkIndex = 0; chunkIndex < ASSET_FILE_DATA_CHUNKS; chunkIndex++) - { - const auto chunk = context.Output.Header.Chunks[chunkIndex]; - if (!chunk) - continue; - - int32 numSamples; - switch (oldHeader.Format) - { - case AudioFormat::Raw: - { - numSamples = chunk->Size() / (oldHeader.Info.BitDepth / 8); - break; - } - case AudioFormat::Vorbis: - { -#if COMPILE_WITH_OGG_VORBIS - OggVorbisDecoder decoder; - MemoryReadStream stream(chunk->Get(), chunk->Size()); - AudioDataInfo outInfo; - if (!decoder.Open(&stream, outInfo, 0)) - { - LOG(Warning, "Audio data open failed (OggVorbisDecoder)."); - return true; - } - numSamples = outInfo.NumSamples; -#else - LOG(Warning, "OggVorbisDecoder is disabled."); - return true; -#endif - break; - } - default: - LOG(Warning, "Unknown audio data format."); - return true; - } - newHeader.SamplesPerChunk[chunkIndex] = numSamples; - } - context.Output.CustomData.Copy(&newHeader); - - // Validate total amount of samples calculated from the asset chunks - uint32 totalSamplesInChunks = 0; - for (int32 chunkIndex = 0; chunkIndex < ASSET_FILE_DATA_CHUNKS; chunkIndex++) - totalSamplesInChunks += newHeader.SamplesPerChunk[chunkIndex]; - if (totalSamplesInChunks != newHeader.Info.NumSamples) - { - LOG(Warning, "Invalid amount of audio data samples in data chunks {0}, audio clip has: {1}.", totalSamplesInChunks, newHeader.Info.NumSamples); - return true; - } - - return false; - } }; #endif diff --git a/Source/Engine/Content/Upgraders/FontAssetUpgrader.h b/Source/Engine/Content/Upgraders/FontAssetUpgrader.h index 4377f1904..4149816cd 100644 --- a/Source/Engine/Content/Upgraders/FontAssetUpgrader.h +++ b/Source/Engine/Content/Upgraders/FontAssetUpgrader.h @@ -5,7 +5,6 @@ #if USE_EDITOR #include "BinaryAssetUpgrader.h" -#include "Engine/Render2D/FontAsset.h" /// /// Font Asset Upgrader @@ -21,55 +20,10 @@ public: { static const Upgrader upgraders[] = { - { 1, 2, &Upgrade_1_To_2 }, - { 2, 3, &Upgrade_2_To_3 }, + {}, }; setup(upgraders, ARRAY_COUNT(upgraders)); } - -private: - // ============================================ - // Version 1: - // Designed: long time ago in a galaxy far far away - // Custom Data: not used - // Chunk 0: Header - // Chunk 1: Font File data - // ============================================ - // Version 2: - // Designed: 4/20/2017 - // Custom Data: not used - // Chunk 0: Font File data - // ============================================ - // Version 3: - // Designed: 10/24/2019 - // Custom Data: Header1 - // Chunk 0: Font File data - // ============================================ - - typedef FontOptions Header1; - - static bool Upgrade_1_To_2(AssetMigrationContext& context) - { - ASSERT(context.Input.SerializedVersion == 1 && context.Output.SerializedVersion == 2); - - if (context.AllocateChunk(0)) - return true; - context.Output.Header.Chunks[0]->Data.Copy(context.Input.Header.Chunks[1]->Data); - - return false; - } - - static bool Upgrade_2_To_3(AssetMigrationContext& context) - { - ASSERT(context.Input.SerializedVersion == 2 && context.Output.SerializedVersion == 3); - - Header1 header; - header.Hinting = FontHinting::Default; - header.Flags = FontFlags::AntiAliasing; - context.Output.CustomData.Copy(&header); - - return CopyChunk(context, 0); - } }; #endif diff --git a/Source/Engine/Content/Upgraders/MaterialInstanceUpgrader.h b/Source/Engine/Content/Upgraders/MaterialInstanceUpgrader.h index 75029e10e..e2081e3d3 100644 --- a/Source/Engine/Content/Upgraders/MaterialInstanceUpgrader.h +++ b/Source/Engine/Content/Upgraders/MaterialInstanceUpgrader.h @@ -5,10 +5,6 @@ #if USE_EDITOR #include "BinaryAssetUpgrader.h" -#include "Engine/Core/Core.h" -#include "Engine/Platform/Platform.h" -#include "Engine/Serialization/MemoryReadStream.h" -#include "Engine/Serialization/MemoryWriteStream.h" /// /// Material Instance Upgrader @@ -24,86 +20,10 @@ public: { static const Upgrader upgraders[] = { - { 1, 3, &Upgrade_1_To_3 }, - { 3, 4, &Upgrade_3_To_4 }, + {}, }; setup(upgraders, ARRAY_COUNT(upgraders)); } - -private: - // ============================================ - // Version 4: - // Designed: 5/18/2017 - // Custom Data: not used - // Chunk 0: - // - Parent material: Guid - // - Material Params - // ============================================ - // Version 3: - // Designed: 1/24/2016 - // Custom Data: not used - // Chunk 0: - // - Magic Code: int32 ('MI\0@', 1073760589) - // - Version: int32 - // - Parent material: Guid - // - Material Params - // - Ending char: 1 byte (~) - // ============================================ - - static bool Upgrade_1_To_3(AssetMigrationContext& context) - { - ASSERT(context.Input.SerializedVersion == 1 && context.Output.SerializedVersion == 3); - - auto chunk = context.Input.Header.Chunks[0]; - if (chunk == nullptr || chunk->IsMissing()) - { - LOG(Warning, "Missing material instance data chunk."); - return true; - } - if (context.AllocateChunk(0)) - return true; - context.Output.Header.Chunks[0]->Data.Copy(chunk->Data); - - return false; - } - - static bool Upgrade_3_To_4(AssetMigrationContext& context) - { - ASSERT(context.Input.SerializedVersion == 3 && context.Output.SerializedVersion == 4); - - auto chunk = context.Input.Header.Chunks[0]; - if (chunk == nullptr || chunk->IsMissing()) - { - LOG(Warning, "Missing material instance data chunk."); - return true; - } - if (context.AllocateChunk(0)) - return true; - MemoryReadStream inStream(chunk->Data.Get(), chunk->Data.Length()); - MemoryWriteStream outStream(chunk->Size()); - - // Header - int32 magicCode; - inStream.ReadInt32(&magicCode); - int32 version; - inStream.ReadInt32(&version); - if (magicCode != 1073760589 || version != 3) - { - LOG(Warning, "Invalid material instance header."); - return true; - } - - // Parent material + Params - // TODO: add tool function to copy stream -> stream - while (inStream.CanRead()) - { - byte b = inStream.ReadByte(); - outStream.WriteByte(b); - } - context.Output.Header.Chunks[0]->Data.Copy(outStream.GetHandle(), outStream.GetPosition()); - - return false; - } }; #endif diff --git a/Source/Engine/Content/Upgraders/ModelAssetUpgrader.h b/Source/Engine/Content/Upgraders/ModelAssetUpgrader.h index 712b5eda9..8b7d70084 100644 --- a/Source/Engine/Content/Upgraders/ModelAssetUpgrader.h +++ b/Source/Engine/Content/Upgraders/ModelAssetUpgrader.h @@ -5,12 +5,6 @@ #if USE_EDITOR #include "BinaryAssetUpgrader.h" -#include "Engine/Core/Core.h" -#include "Engine/Platform/Platform.h" -#include "Engine/Serialization/MemoryReadStream.h" -#include "Engine/Serialization/MemoryWriteStream.h" -#include "Engine/Graphics/Models/ModelData.h" -#include "Engine/Content/Asset.h" /// /// Model Asset Upgrader @@ -26,1202 +20,10 @@ public: { static const Upgrader upgraders[] = { - { 24, 25, &Upgrade_With_Repack }, // [Deprecated on 28.04.2023, expires on 01.01.2024] - { 23, 24, &Upgrade_22OrNewer_To_Newest }, // [Deprecated on 28.04.2023, expires on 01.01.2024] - { 22, 24, &Upgrade_22OrNewer_To_Newest }, // [Deprecated on 28.04.2023, expires on 01.01.2024] - { 1, 24, &Upgrade_Old_To_Newest }, // [Deprecated on 28.04.2023, expires on 01.01.2024] + {}, }; setup(upgraders, ARRAY_COUNT(upgraders)); } - -private: - // ============================================ - // Version 25: - // The same as version 24 except Vertex Buffer 1 has `Color32 Color` component per vertex added - // ============================================ - // Version 24: - // Designed: 9/24/2017 - // Custom Data: not used - // Chunk 0: - // - Min Screen Size: float - // - Amount of material slots: int32 - // - For each material slot: - // - Material: Guid - // - Shadows Mode: byte - // - Name: String (offset: 11) - // - Amount of LODs: byte - // - For each LOD: - // - Screen Size: float - // - Amount of meshes: uint16 - // - For each mesh: - // - Material Slot index: int32 - // - Box: BoundingBox - // - Sphere: BoundingSphere - // - HasLightmapUVs: bool - // Next chunks: (the highest LOD is at chunk no. 1, followed by the lower LODs: - // - For each mesh in the LOD: - // - Vertices Count: uint32 - // - Triangles Count: uint32 - // - Vertex Buffer 0: byte[] - // - For each vertex - // - Position : R32G32B32_Float - // - Vertex Buffer 1: byte[] - // - For each vertex - // - TexCoord : R16G16_Float - // - Normal : R10G10B10A2_UNorm - // - Tangent : R10G10B10A2_UNorm - // - LightampUV : R16G16_Float - // - Index Buffer: uint16[] or uint32[] (based on amount of triangles) - // ============================================ - // Version 23: - // Designed: 9/18/2017 - // Custom Data: not used - // Chunk 0: - // - Amount of material slots: int32 - // - For each material slot: - // - Material: Guid - // - Shadows Mode: byte - // - Name: String (offset: 11) - // - Amount of LODs: byte - // - For each LOD: - // - Amount of meshes: uint16 - // - For each mesh: - // - Material Slot index: int32 - // - Box: BoundingBox - // - Sphere: BoundingSphere - // Next chunks: (the highest LOD is at chunk no. 1, followed by the lower LODs: - // - For each mesh in the LOD: - // - Vertices Count: uint32 - // - Triangles Count: uint32 - // - Vertex Buffer 0: byte[] - // - For each vertex - // - Position : R32G32B32_Float - // - Vertex Buffer 1: byte[] - // - For each vertex - // - TexCoord : R16G16_Float - // - Normal : R10G10B10A2_UNorm - // - Tangent : R10G10B10A2_UNorm - // - LightampUV : R16G16_Float - // - Index Buffer: uint16[] or uint32[] (based on amount of triangles) - // ============================================ - // Version 22: - // Designed: 4/24/2017 - // Custom Data: not used - // Chunk 0: - // - Amount of LODs: byte - // - For each LOD: - // - Amount of meshes: uint16 - // - For each mesh: - // - Name: String (offset: 7) - // - Force Two Sided: bool - // - Cast Shadows: bool - // - Material ID: Guid - // - Box: BoundingBox - // - Sphere: BoundingSphere - // Next chunks: (the highest LOD is at chunk no. 1, followed by the lower LODs: - // - For each mesh in the LOD: - // - Vertices Count: uint32 - // - Triangles Count: uint32 - // - Vertex Buffer 0: byte[] - // - For each vertex - // - Position : R32G32B32_Float - // - Vertex Buffer 1: byte[] - // - For each vertex - // - TexCoord : R16G16_Float - // - Normal : R10G10B10A2_UNorm - // - Tangent : R10G10B10A2_UNorm - // - LightampUV : R16G16_Float - // - Index Buffer: uint16[] or uint32[] (based on amount of triangles) - // ============================================ - - static Asset::LoadResult LoadOld(AssetMigrationContext& context, int32 version, ReadStream& headerStream, ModelData& modelData) - { - // Load version - Asset::LoadResult result; - switch (version) - { - case 25: - result = loadVersion25(context, &headerStream, &modelData); - break; - case 24: - result = loadVersion24(context, &headerStream, &modelData); - break; - case 23: - result = loadVersion23(context, &headerStream, &modelData); - break; - case 22: - result = loadVersion22(context, &headerStream, &modelData); - break; - case 20: - result = loadVersion20(context, &headerStream, &modelData); - break; - case 19: - result = loadVersion19(context, &headerStream, &modelData); - break; - case 18: - result = loadVersion18(context, &headerStream, &modelData); - break; - case 17: - result = loadVersion17(context, &headerStream, &modelData); - break; - case 16: - result = loadVersion16(context, &headerStream, &modelData); - break; - case 15: - result = loadVersion15(context, &headerStream, &modelData); - break; - default: - LOG(Warning, "Unsupported model data version."); - result = Asset::LoadResult::InvalidData; - break; - } - - return result; - } - - static Asset::LoadResult loadVersion25(AssetMigrationContext& context, ReadStream* headerStream, ModelData* data) - { - // Min Screen Size - headerStream->ReadFloat(&data->MinScreenSize); - - // Amount of material slots - int32 materialSlotsCount; - headerStream->ReadInt32(&materialSlotsCount); - data->Materials.Resize(materialSlotsCount, false); - - // For each material slot - for (int32 i = 0; i < materialSlotsCount; i++) - { - auto& slot = data->Materials[i]; - - // Material - headerStream->Read(slot.AssetID); - - // Shadows Mode - slot.ShadowsMode = static_cast(headerStream->ReadByte()); - - // Name - headerStream->ReadString(&slot.Name, 11); - } - - // Amount of LODs - const int32 lodsCount = headerStream->ReadByte(); - data->LODs.Resize(lodsCount, false); - - // For each LOD - for (int32 lodIndex = 0; lodIndex < lodsCount; lodIndex++) - { - auto& lod = data->LODs[lodIndex]; - - // Screen Size - headerStream->ReadFloat(&lod.ScreenSize); - - // Amount of meshes (and material slots for older formats) - uint16 meshesCount; - headerStream->ReadUint16(&meshesCount); - lod.Meshes.Resize(meshesCount); - lod.Meshes.SetAll(nullptr); - - // Get meshes data - { - auto lodData = context.Input.Header.Chunks[1 + lodIndex]; - MemoryReadStream stream(lodData->Get(), lodData->Size()); - - // Load LOD for each mesh - for (int32 meshIndex = 0; meshIndex < meshesCount; meshIndex++) - { - // Load mesh data - uint32 vertices; - stream.ReadUint32(&vertices); - uint32 triangles; - stream.ReadUint32(&triangles); - if (vertices == 0 || triangles == 0) - return Asset::LoadResult::InvalidData; - - // Vertex buffers - auto vb0 = stream.Move(vertices); - auto vb1 = stream.Move(vertices); - bool hasColors = stream.ReadBool(); - VB2ElementType18* vb2 = nullptr; - if (hasColors) - { - vb2 = stream.Move(vertices); - } - - // Index Buffer - uint32 indicesCount = triangles * 3; - bool use16BitIndexBuffer = indicesCount <= MAX_uint16; - uint32 ibStride = use16BitIndexBuffer ? sizeof(uint16) : sizeof(uint32); - auto ib = stream.Move(indicesCount * ibStride); - - // Allocate mesh - lod.Meshes[meshIndex] = New(); - auto& mesh = *lod.Meshes[meshIndex]; - - // Copy data - mesh.InitFromModelVertices(vb0, vb1, vb2, vertices); - mesh.SetIndexBuffer(ib, indicesCount); - } - } - - // For each mesh - for (int32 meshIndex = 0; meshIndex < meshesCount; meshIndex++) - { - auto& mesh = *lod.Meshes[meshIndex]; - - // Material Slot index - int32 materialSlotIndex; - headerStream->ReadInt32(&materialSlotIndex); - if (materialSlotIndex < 0 || materialSlotIndex >= materialSlotsCount) - { - LOG(Warning, "Invalid material slot index {0} for mesh {1}. Slots count: {2}.", materialSlotIndex, meshIndex, materialSlotsCount); - return Asset::LoadResult::InvalidData; - } - - // Box - BoundingBox box; - headerStream->Read(box); - - // Sphere - BoundingSphere sphere; - headerStream->Read(sphere); - - // Has Lightmap UVs - bool hasLightmapUVs = headerStream->ReadBool(); - if (!hasLightmapUVs) - mesh.LightmapUVs.Resize(0); - } - } - - return Asset::LoadResult::Ok; - } - - static Asset::LoadResult loadVersion24(AssetMigrationContext& context, ReadStream* headerStream, ModelData* data) - { - // Min Screen Size - headerStream->ReadFloat(&data->MinScreenSize); - - // Amount of material slots - int32 materialSlotsCount; - headerStream->ReadInt32(&materialSlotsCount); - data->Materials.Resize(materialSlotsCount, false); - - // For each material slot - for (int32 i = 0; i < materialSlotsCount; i++) - { - auto& slot = data->Materials[i]; - - // Material - headerStream->Read(slot.AssetID); - - // Shadows Mode - slot.ShadowsMode = static_cast(headerStream->ReadByte()); - - // Name - headerStream->ReadString(&slot.Name, 11); - } - - // Amount of LODs - const int32 lodsCount = headerStream->ReadByte(); - data->LODs.Resize(lodsCount, false); - - // For each LOD - for (int32 lodIndex = 0; lodIndex < lodsCount; lodIndex++) - { - auto& lod = data->LODs[lodIndex]; - - // Screen Size - headerStream->ReadFloat(&lod.ScreenSize); - - // Amount of meshes (and material slots for older formats) - uint16 meshesCount; - headerStream->ReadUint16(&meshesCount); - lod.Meshes.Resize(meshesCount); - lod.Meshes.SetAll(nullptr); - - // Get meshes data - { - auto lodData = context.Input.Header.Chunks[1 + lodIndex]; - MemoryReadStream stream(lodData->Get(), lodData->Size()); - - // Load LOD for each mesh - for (int32 meshIndex = 0; meshIndex < meshesCount; meshIndex++) - { - // Load mesh data - uint32 vertices; - stream.ReadUint32(&vertices); - uint32 triangles; - stream.ReadUint32(&triangles); - if (vertices == 0 || triangles == 0) - return Asset::LoadResult::InvalidData; - - // Vertex buffers - auto vb0 = stream.Move(vertices); - auto vb1 = stream.Move(vertices); - - // Index Buffer - uint32 indicesCount = triangles * 3; - bool use16BitIndexBuffer = indicesCount <= MAX_uint16; - uint32 ibStride = use16BitIndexBuffer ? sizeof(uint16) : sizeof(uint32); - auto ib = stream.Move(indicesCount * ibStride); - - // Allocate mesh - lod.Meshes[meshIndex] = New(); - auto& mesh = *lod.Meshes[meshIndex]; - - // Copy data - mesh.InitFromModelVertices(vb0, vb1, vertices); - mesh.SetIndexBuffer(ib, indicesCount); - } - } - - // For each mesh - for (int32 meshIndex = 0; meshIndex < meshesCount; meshIndex++) - { - auto& mesh = *lod.Meshes[meshIndex]; - - // Material Slot index - int32 materialSlotIndex; - headerStream->ReadInt32(&materialSlotIndex); - if (materialSlotIndex < 0 || materialSlotIndex >= materialSlotsCount) - { - LOG(Warning, "Invalid material slot index {0} for mesh {1}. Slots count: {2}.", materialSlotIndex, meshIndex, materialSlotsCount); - return Asset::LoadResult::InvalidData; - } - - // Box - BoundingBox box; - headerStream->Read(box); - - // Sphere - BoundingSphere sphere; - headerStream->Read(sphere); - - // Has Lightmap UVs - bool hasLightmapUVs = headerStream->ReadBool(); - if (!hasLightmapUVs) - mesh.LightmapUVs.Resize(0); - } - } - - return Asset::LoadResult::Ok; - } - - static Asset::LoadResult loadVersion23(AssetMigrationContext& context, ReadStream* headerStream, ModelData* data) - { - // Amount of material slots - int32 materialSlotsCount; - headerStream->ReadInt32(&materialSlotsCount); - data->Materials.Resize(materialSlotsCount, false); - - // For each material slot - for (int32 i = 0; i < materialSlotsCount; i++) - { - auto& slot = data->Materials[i]; - - // Material - headerStream->Read(slot.AssetID); - - // Shadows Mode - slot.ShadowsMode = static_cast(headerStream->ReadByte()); - - // Name - headerStream->ReadString(&slot.Name, 11); - } - - // Amount of LODs - const int32 lodsCount = headerStream->ReadByte(); - data->LODs.Resize(lodsCount, false); - - // For each LOD - for (int32 lodIndex = 0; lodIndex < lodsCount; lodIndex++) - { - // Amount of meshes (and material slots for older formats) - uint16 meshesCount; - headerStream->ReadUint16(&meshesCount); - data->LODs[lodIndex].Meshes.Resize(meshesCount); - data->LODs[lodIndex].Meshes.SetAll(nullptr); - - // For each mesh - for (int32 meshIndex = 0; meshIndex < meshesCount; meshIndex++) - { - data->LODs[lodIndex].Meshes[meshIndex] = New(); - auto& meshEntry = *data->LODs[lodIndex].Meshes[meshIndex]; - - // Material Slot index - int32 materialSlotIndex; - headerStream->ReadInt32(&materialSlotIndex); - if (materialSlotIndex < 0 || materialSlotIndex >= materialSlotsCount) - { - LOG(Warning, "Invalid material slot index {0} for mesh {1}. Slots count: {2}.", materialSlotIndex, meshIndex, materialSlotsCount); - return Asset::LoadResult::InvalidData; - } - meshEntry.MaterialSlotIndex = materialSlotIndex; - - // Box - BoundingBox box; - headerStream->Read(box); - - // Sphere - BoundingSphere sphere; - headerStream->Read(sphere); - } - - // Get meshes data - { - auto lodData = context.Input.Header.Chunks[1 + lodIndex]; - MemoryReadStream stream(lodData->Get(), lodData->Size()); - - // Load LOD for each mesh - for (int32 i = 0; i < meshesCount; i++) - { - // Load mesh data - uint32 vertices; - stream.ReadUint32(&vertices); - uint32 triangles; - stream.ReadUint32(&triangles); - if (vertices == 0 || triangles == 0) - return Asset::LoadResult::InvalidData; - - // Vertex buffers - auto vb0 = stream.Move(vertices); - auto vb1 = stream.Move(vertices); - - // Index Buffer - uint32 indicesCount = triangles * 3; - bool use16BitIndexBuffer = indicesCount <= MAX_uint16; - uint32 ibStride = use16BitIndexBuffer ? sizeof(uint16) : sizeof(uint32); - auto ib = stream.Move(indicesCount * ibStride); - - // Copy data - auto& mesh = *data->LODs[lodIndex].Meshes[i]; - mesh.InitFromModelVertices(vb0, vb1, vertices); - mesh.SetIndexBuffer(ib, indicesCount); - } - } - } - - return Asset::LoadResult::Ok; - } - - static Asset::LoadResult loadVersion22(AssetMigrationContext& context, ReadStream* headerStream, ModelData* data) - { - // Amount of LODs - const int32 lodsCount = headerStream->ReadByte(); - if (lodsCount != 1) - return Asset::LoadResult::InvalidData; - data->LODs.Resize(lodsCount, false); - - // Amount of meshes (and material slots for older formats) - uint16 meshesCount; - headerStream->ReadUint16(&meshesCount); - data->Materials.Resize(meshesCount, false); - data->LODs[0].Meshes.Resize(meshesCount); - - // For each mesh - for (int32 i = 0; i < meshesCount; i++) - { - data->LODs[0].Meshes[i] = New(); - auto& meshEntry = *data->LODs[0].Meshes[i]; - auto& slot = data->Materials[i]; - - // Conversion from older format: 1-1 material slot - mesh mapping, new format allows to use the same material slot for many meshes across different lods - meshEntry.MaterialSlotIndex = i; - - // Name - headerStream->ReadString(&slot.Name, 7); - - // Force Two Sided - headerStream->ReadBool(); - - // Cast Shadows - const bool castShadows = headerStream->ReadBool(); - slot.ShadowsMode = castShadows ? ShadowsCastingMode::All : ShadowsCastingMode::None; - - // Default material ID - headerStream->Read(slot.AssetID); - - // Box - BoundingBox box; - headerStream->Read(box); - - // Sphere - BoundingSphere sphere; - headerStream->Read(sphere); - } - - { - // Get data - auto lodData = context.Input.Header.Chunks[1]; - MemoryReadStream stream(lodData->Get(), lodData->Size()); - - // Load LOD for each mesh - for (int32 i = 0; i < meshesCount; i++) - { - // Load mesh data - uint32 vertices; - stream.ReadUint32(&vertices); - uint32 triangles; - stream.ReadUint32(&triangles); - if (vertices == 0 || triangles == 0) - return Asset::LoadResult::InvalidData; - - // Vertex buffers - auto vb0 = stream.Move(vertices); - auto vb1 = stream.Move(vertices); - - // Index Buffer - uint32 indicesCount = triangles * 3; - bool use16BitIndexBuffer = indicesCount <= MAX_uint16; - uint32 ibStride = use16BitIndexBuffer ? sizeof(uint16) : sizeof(uint32); - auto ib = stream.Move(indicesCount * ibStride); - - // Copy data - auto& mesh = *data->LODs[0].Meshes[i]; - mesh.InitFromModelVertices(vb0, vb1, vertices); - mesh.SetIndexBuffer(ib, indicesCount); - } - } - - return Asset::LoadResult::Ok; - } - - static Asset::LoadResult loadVersion20(AssetMigrationContext& context, ReadStream* headerStream, ModelData* data) - { - // Amount of meshes (and material slots for older formats) - uint16 meshesCount; - headerStream->ReadUint16(&meshesCount); - data->Materials.Resize(meshesCount, false); - data->LODs.Resize(1, false); - data->LODs[0].Meshes.Resize(meshesCount); - - // Amount of LODs - int32 lodsCount = headerStream->ReadByte(); - if (lodsCount != 1) - return Asset::LoadResult::InvalidData; - - // For each mesh - for (int32 i = 0; i < meshesCount; i++) - { - data->LODs[0].Meshes[i] = New(); - auto& meshEntry = *data->LODs[0].Meshes[i]; - auto& slot = data->Materials[i]; - - // Name - headerStream->ReadString(&slot.Name, 7); - - // Force Two Sided - headerStream->ReadBool(); - - // Default material ID - headerStream->Read(slot.AssetID); - - // Box - BoundingBox box; - headerStream->Read(box); - - // Sphere - BoundingSphere sphere; - headerStream->Read(sphere); - } - - { - // Get data - auto lodData = context.Input.Header.Chunks[1]; - MemoryReadStream stream(lodData->Get(), lodData->Size()); - - // Load LOD for each mesh - for (int32 i = 0; i < meshesCount; i++) - { - // Load mesh data - uint32 vertices; - stream.ReadUint32(&vertices); - uint32 triangles; - stream.ReadUint32(&triangles); - if (vertices == 0 || triangles == 0) - return Asset::LoadResult::InvalidData; - - // Vertex buffers - auto vb0 = stream.Move(vertices); - auto vb1 = stream.Move(vertices); - - // Index Buffer - uint32 indicesCount = triangles * 3; - bool use16BitIndexBuffer = indicesCount <= MAX_uint16; - uint32 ibStride = use16BitIndexBuffer ? sizeof(uint16) : sizeof(uint32); - auto ib = stream.Move(indicesCount * ibStride); - - // Copy data - auto& mesh = *data->LODs[0].Meshes[i]; - mesh.InitFromModelVertices(vb0, vb1, vertices); - mesh.SetIndexBuffer(ib, indicesCount); - } - } - - return Asset::LoadResult::Ok; - } - - static Asset::LoadResult loadVersion19(AssetMigrationContext& context, ReadStream* headerStream, ModelData* data) - { - // Amount of meshes (and material slots for older formats) - uint16 meshesCount; - headerStream->ReadUint16(&meshesCount); - data->Materials.Resize(meshesCount, false); - data->LODs.Resize(1, false); - data->LODs[0].Meshes.Resize(meshesCount); - - // Amount of LODs - int32 lodsCount = headerStream->ReadByte(); - if (lodsCount != 1) - return Asset::LoadResult::InvalidData; - - // For each mesh - for (int32 i = 0; i < meshesCount; i++) - { - data->LODs[0].Meshes[i] = New(); - auto& meshEntry = *data->LODs[0].Meshes[i]; - auto& slot = data->Materials[i]; - - // Name - headerStream->ReadString(&slot.Name, 7); - - // Force Two Sided - headerStream->ReadBool(); - - // Default material ID - headerStream->Read(slot.AssetID); - - // Box - BoundingBox box; - headerStream->Read(box); - - // Sphere - BoundingSphere sphere; - headerStream->Read(sphere); - } - - // Load all LODs - { - // Get data - auto lodData = context.Input.Header.Chunks[1]; - MemoryReadStream stream(lodData->Get(), lodData->Size()); - - // Load LOD for each mesh - for (int32 i = 0; i < meshesCount; i++) - { - // Load mesh data - uint32 vertices; - stream.ReadUint32(&vertices); - uint32 triangles; - stream.ReadUint32(&triangles); - if (vertices == 0 || triangles == 0) - return Asset::LoadResult::InvalidData; - - // Vertex buffers - auto vb0 = stream.Move(vertices); - auto vb1 = stream.Move(vertices); - - // Index Buffer - uint32 indicesCount = triangles * 3; - bool use16BitIndexBuffer = indicesCount <= MAX_uint16; - uint32 ibStride = use16BitIndexBuffer ? sizeof(uint16) : sizeof(uint32); - auto ib = stream.Move(indicesCount * ibStride); - - // Copy data - auto& mesh = *data->LODs[0].Meshes[i]; - mesh.InitFromModelVertices(vb0, vb1, vertices); - mesh.SetIndexBuffer(ib, indicesCount); - } - } - - return Asset::LoadResult::Ok; - } - - static Asset::LoadResult loadVersion18(AssetMigrationContext& context, ReadStream* headerStream, ModelData* data) - { - // Amount of meshes (and material slots for older formats) - uint16 meshesCount; - headerStream->ReadUint16(&meshesCount); - data->Materials.Resize(meshesCount, false); - data->LODs.Resize(1, false); - data->LODs[0].Meshes.Resize(meshesCount); - - // Amount of LODs - int32 lodsCount = headerStream->ReadByte(); - if (lodsCount != 1) - return Asset::LoadResult::InvalidData; - - // Options version code - uint32 optionsVersionCode; - headerStream->ReadUint32(&optionsVersionCode); - - // For each mesh - for (int32 i = 0; i < meshesCount; i++) - { - data->LODs[0].Meshes[i] = New(); - auto& meshEntry = *data->LODs[0].Meshes[i]; - auto& slot = data->Materials[i]; - - // Name - headerStream->ReadString(&slot.Name, 7); - - // Local Transform - Transform transform; - headerStream->Read(transform); - - // Force Two Sided - headerStream->ReadBool(); - - // Default material ID - headerStream->Read(slot.AssetID); - - // Corners - BoundingBox box; - headerStream->Read(box); - } - - // Load all LODs - { - // Get data - auto lodData = context.Input.Header.Chunks[1]; - MemoryReadStream stream(lodData->Get(), lodData->Size()); - - // Load LOD for each mesh - for (int32 i = 0; i < meshesCount; i++) - { - // Load mesh data - uint32 vertices; - stream.ReadUint32(&vertices); - uint32 triangles; - stream.ReadUint32(&triangles); - if (vertices == 0 || triangles == 0) - return Asset::LoadResult::InvalidData; - - // Vertex buffers - auto vb0 = stream.Move(vertices); - auto vb1 = stream.Move(vertices); - - // Index Buffer - uint32 indicesCount = triangles * 3; - bool use16BitIndexBuffer = indicesCount <= MAX_uint16; - uint32 ibStride = use16BitIndexBuffer ? sizeof(uint16) : sizeof(uint32); - auto ib = stream.Move(indicesCount * ibStride); - - // Copy data - auto& mesh = *data->LODs[0].Meshes[i]; - mesh.InitFromModelVertices(vb0, vb1, vertices); - mesh.SetIndexBuffer(ib, indicesCount); - } - } - - return Asset::LoadResult::Ok; - } - - static Asset::LoadResult loadVersion17(AssetMigrationContext& context, ReadStream* headerStream, ModelData* data) - { - // Amount of meshes (and material slots for older formats) - uint16 meshesCount; - headerStream->ReadUint16(&meshesCount); - data->Materials.Resize(meshesCount, false); - data->LODs.Resize(1, false); - data->LODs[0].Meshes.Resize(meshesCount); - - // Amount of LODs - int32 lodsCount = headerStream->ReadByte(); - if (lodsCount != 1) - return Asset::LoadResult::InvalidData; - - // Options version code - uint32 optionsVersionCode; - headerStream->ReadUint32(&optionsVersionCode); - - // For each mesh - for (int32 i = 0; i < meshesCount; i++) - { - data->LODs[0].Meshes[i] = New(); - auto& meshEntry = *data->LODs[0].Meshes[i]; - auto& slot = data->Materials[i]; - - // Name - headerStream->ReadString(&slot.Name, 7); - - // Local Transform - Transform transform; - headerStream->Read(transform); - - // Force Two Sided - headerStream->ReadBool(); - - // Default material ID - headerStream->Read(slot.AssetID); - - // Corners - Vector3 corner; - for (int32 cornerIndex = 0; cornerIndex < 8; cornerIndex++) - headerStream->Read(corner); - } - - // Load all LODs - { - // Get data - auto lodData = context.Input.Header.Chunks[1]; - MemoryReadStream stream(lodData->Get(), lodData->Size()); - - // Load LOD for each mesh - for (int32 i = 0; i < meshesCount; i++) - { - // Load mesh data - uint32 vertices; - stream.ReadUint32(&vertices); - uint32 triangles; - stream.ReadUint32(&triangles); - if (vertices == 0 || triangles == 0) - return Asset::LoadResult::InvalidData; - - // Vertex buffers - auto vb0 = stream.Move(vertices); - auto vb1 = stream.Move(vertices); - - // Index Buffer - uint32 indicesCount = triangles * 3; - bool use16BitIndexBuffer = indicesCount <= MAX_uint16; - uint32 ibStride = use16BitIndexBuffer ? sizeof(uint16) : sizeof(uint32); - auto ib = stream.Move(indicesCount * ibStride); - - // Copy data - auto& mesh = *data->LODs[0].Meshes[i]; - mesh.InitFromModelVertices(vb0, vb1, vertices); - mesh.SetIndexBuffer(ib, indicesCount); - -#if COMPILE_WITH_MODEL_TOOL - if (mesh.GenerateLightmapUVs()) - return Asset::LoadResult::Failed; -#endif - } - } - - return Asset::LoadResult::Ok; - } - - static Asset::LoadResult loadVersion16(AssetMigrationContext& context, ReadStream* headerStream, ModelData* data) - { - // Amount of meshes (and material slots for older formats) - uint16 meshesCount; - headerStream->ReadUint16(&meshesCount); - data->Materials.Resize(meshesCount, false); - data->LODs.Resize(1, false); - data->LODs[0].Meshes.Resize(meshesCount); - - // Amount of LODs - int32 lodsCount = headerStream->ReadByte(); - if (lodsCount != 1) - return Asset::LoadResult::InvalidData; - - // Options version code - uint32 optionsVersionCode; - headerStream->ReadUint32(&optionsVersionCode); - - // For each mesh - for (int32 i = 0; i < meshesCount; i++) - { - data->LODs[0].Meshes[i] = New(); - auto& meshEntry = *data->LODs[0].Meshes[i]; - auto& slot = data->Materials[i]; - - // Name - headerStream->ReadString(&slot.Name, 7); - - // Local Transform - Transform transform; - headerStream->Read(transform); - - // Force Two Sided - headerStream->ReadBool(); - - // Default material ID - headerStream->Read(slot.AssetID); - } - - // Load all LODs - { - // Get data - auto lodData = context.Input.Header.Chunks[1]; - MemoryReadStream stream(lodData->Get(), lodData->Size()); - - // Load LOD for each mesh - for (int32 i = 0; i < meshesCount; i++) - { - // Load mesh data - uint32 vertices; - stream.ReadUint32(&vertices); - uint32 triangles; - stream.ReadUint32(&triangles); - if (vertices == 0 || triangles == 0) - return Asset::LoadResult::InvalidData; - - // Vertex buffers - auto vb0 = stream.Move(vertices); - auto vb1 = stream.Move(vertices); - - // Index Buffer - uint32 indicesCount = triangles * 3; - bool use16BitIndexBuffer = indicesCount <= MAX_uint16; - uint32 ibStride = use16BitIndexBuffer ? sizeof(uint16) : sizeof(uint32); - auto ib = stream.Move(indicesCount * ibStride); - - // Copy data - auto& mesh = *data->LODs[0].Meshes[i]; - mesh.InitFromModelVertices(vb0, vb1, vertices); - mesh.SetIndexBuffer(ib, indicesCount); - -#if COMPILE_WITH_MODEL_TOOL - if (mesh.GenerateLightmapUVs()) - return Asset::LoadResult::Failed; -#endif - } - } - - return Asset::LoadResult::Ok; - } - - static Asset::LoadResult loadVersion15(AssetMigrationContext& context, ReadStream* headerStream, ModelData* data) - { - // Amount of meshes (and material slots for older formats) - uint16 meshesCount; - headerStream->ReadUint16(&meshesCount); - data->Materials.Resize(meshesCount, false); - data->LODs.Resize(1, false); - data->LODs[0].Meshes.Resize(meshesCount); - - // Amount of LODs - int32 lodsCount = headerStream->ReadByte(); - if (lodsCount != 1) - return Asset::LoadResult::InvalidData; - - // Options version code - uint32 optionsVersionCode; - headerStream->ReadUint32(&optionsVersionCode); - - // For each mesh - for (int32 i = 0; i < meshesCount; i++) - { - data->LODs[0].Meshes[i] = New(); - auto& meshEntry = *data->LODs[0].Meshes[i]; - auto& slot = data->Materials[i]; - - // Name - headerStream->ReadString(&slot.Name, 7); - - // Local Transform - Transform transform; - headerStream->Read(transform); - - // Force Two Sided - headerStream->ReadBool(); - - // Default material ID - headerStream->Read(slot.AssetID); - } - - // Load all LODs - for (int32 lodIndex = 0; lodIndex < lodsCount; lodIndex++) - { - // Get data - auto lodData = context.Input.Header.Chunks[1]; - MemoryReadStream stream(lodData->Get(), lodData->Size()); - - // Load LOD for each mesh - for (int32 i = 0; i < meshesCount; i++) - { - // Load mesh data - uint32 vertices; - stream.ReadUint32(&vertices); - uint32 triangles; - stream.ReadUint32(&triangles); - if (vertices == 0 || triangles == 0) - return Asset::LoadResult::InvalidData; - - // Vertex buffer - auto vb = stream.Move(vertices); - - // Index Buffer - uint32 indicesCount = triangles * 3; - bool use16BitIndexBuffer = indicesCount <= MAX_uint16; - uint32 ibStride = use16BitIndexBuffer ? sizeof(uint16) : sizeof(uint32); - auto ib = stream.Move(indicesCount * ibStride); - - // Copy data - auto& mesh = *data->LODs[0].Meshes[i]; - mesh.InitFromModelVertices(vb, vertices); - mesh.SetIndexBuffer(ib, indicesCount); - -#if COMPILE_WITH_MODEL_TOOL - if (mesh.GenerateLightmapUVs()) - return Asset::LoadResult::Failed; -#endif - } - } - - return Asset::LoadResult::Ok; - } - - static bool Upgrade_22OrNewer_To_Newest(AssetMigrationContext& context) - { - // Get header chunk - auto chunk0 = context.Input.Header.Chunks[0]; - if (chunk0 == nullptr || chunk0->IsMissing()) - return true; - MemoryReadStream headerStream(chunk0->Get(), chunk0->Size()); - - // Load model data from the older format - ModelData modelData; - auto result = LoadOld(context, context.Input.SerializedVersion, headerStream, modelData); - if (result != Asset::LoadResult::Ok) - { - LOG(Warning, "Model old-format data conversion failed."); - return true; - } - - // Pack model header - { - if (context.AllocateChunk(0)) - return true; - - MemoryWriteStream newHeaderStream(512); - if (modelData.Pack2ModelHeader(&newHeaderStream)) - return true; - context.Output.Header.Chunks[0]->Data.Copy(newHeaderStream.GetHandle(), newHeaderStream.GetPosition()); - } - - // Copy LODs - for (int32 lodIndex = 0; lodIndex < modelData.LODs.Count(); lodIndex++) - { - int32 chunkIndex = lodIndex + 1; - auto srcLodData = context.Input.Header.Chunks[chunkIndex]; - if (srcLodData == nullptr || srcLodData->IsMissing()) - { - LOG(Warning, "Missing model LOD data chunk"); - return true; - } - if (context.AllocateChunk(chunkIndex)) - return true; - context.Output.Header.Chunks[chunkIndex]->Data.Copy(context.Input.Header.Chunks[chunkIndex]->Data); - } - - return false; - } - - static bool Upgrade_With_Repack(AssetMigrationContext& context) - { - // Get header chunk - auto chunk0 = context.Input.Header.Chunks[0]; - if (chunk0 == nullptr || chunk0->IsMissing()) - return true; - MemoryReadStream headerStream(chunk0->Get(), chunk0->Size()); - - // Load model data from the older format - ModelData modelData; - auto result = LoadOld(context, context.Input.SerializedVersion, headerStream, modelData); - if (result != Asset::LoadResult::Ok) - { - LOG(Warning, "Model old-format data conversion failed."); - return true; - } - - // Pack model header - { - if (context.AllocateChunk(0)) - return true; - - MemoryWriteStream newHeaderStream(512); - if (modelData.Pack2ModelHeader(&newHeaderStream)) - return true; - context.Output.Header.Chunks[0]->Data.Copy(newHeaderStream.GetHandle(), newHeaderStream.GetPosition()); - } - - // Pack model LODs data - MemoryWriteStream stream(4095); - const auto lodsCount = modelData.GetLODsCount(); - for (int32 lodIndex = 0; lodIndex < lodsCount; lodIndex++) - { - stream.SetPosition(0); - - // Pack meshes - auto& meshes = modelData.LODs[lodIndex].Meshes; - for (int32 meshIndex = 0; meshIndex < meshes.Count(); meshIndex++) - { - if (meshes[meshIndex]->Pack2Model(&stream)) - { - LOG(Warning, "Cannot pack mesh."); - return true; - } - } - - const int32 chunkIndex = lodIndex + 1; - if (context.AllocateChunk(chunkIndex)) - return true; - context.Output.Header.Chunks[chunkIndex]->Data.Copy(stream.GetHandle(), stream.GetPosition()); - } - - return false; - } - - static bool Upgrade_Old_To_Newest(AssetMigrationContext& context) - { - ASSERT(context.Input.SerializedVersion == 1); - - // Get header chunk - auto chunk0 = context.Input.Header.Chunks[0]; - if (chunk0 == nullptr || chunk0->IsMissing()) - return true; - MemoryReadStream headerStream(chunk0->Get(), chunk0->Size()); - - // Load header entry - int32 magicCode; - headerStream.ReadInt32(&magicCode); - if (magicCode != -842185139) - { - LOG(Warning, "Invalid header data."); - return true; - } - int32 version; - headerStream.ReadInt32(&version); - - // Load model data from the older format - ModelData modelData; - auto result = LoadOld(context, version, headerStream, modelData); - if (result != Asset::LoadResult::Ok) - { - LOG(Warning, "Model old-format data conversion failed."); - return true; - } - - // Pack model header - { - if (context.AllocateChunk(0)) - return true; - - MemoryWriteStream newHeaderStream(512); - if (modelData.Pack2ModelHeader(&newHeaderStream)) - return true; - context.Output.Header.Chunks[0]->Data.Copy(newHeaderStream.GetHandle(), newHeaderStream.GetPosition()); - } - - // Copy LOD (older versons were using just a single LOD) - { - auto srcLodData = context.Input.Header.Chunks[1]; - if (srcLodData == nullptr || srcLodData->IsMissing()) - { - LOG(Warning, "Missing model LOD data chunk"); - return true; - } - if (context.AllocateChunk(1)) - return true; - context.Output.Header.Chunks[1]->Data.Copy(context.Input.Header.Chunks[1]->Data); - } - - return false; - } }; #endif diff --git a/Source/Engine/Content/Upgraders/ShaderAssetUpgrader.h b/Source/Engine/Content/Upgraders/ShaderAssetUpgrader.h index 09958f96e..97c41dabd 100644 --- a/Source/Engine/Content/Upgraders/ShaderAssetUpgrader.h +++ b/Source/Engine/Content/Upgraders/ShaderAssetUpgrader.h @@ -5,8 +5,6 @@ #if USE_EDITOR #include "BinaryAssetUpgrader.h" -#include "Engine/Platform/Platform.h" -#include "Engine/Graphics/Shaders/Cache/ShaderStorage.h" /// /// Material Asset and Shader Asset Upgrader @@ -22,96 +20,10 @@ public: { static const Upgrader upgraders[] = { - { 18, 19, &Upgrade_18_To_19 }, - { 19, 20, &Upgrade_19_To_20 }, + {}, }; setup(upgraders, ARRAY_COUNT(upgraders)); } - -private: - // ============================================ - // Versions 18,19,20: - // Designed: 7/24/2019 - // Custom Data: Header - // Chunk 0: Material Params - // Chunk 1: Internal SM5 cache - // Chunk 2: Internal SM4 cache - // Chunk 14: Visject Surface data - // Chunk 15: Source code: ANSI text (encrypted) - // ============================================ - - typedef ShaderStorage::Header Header; - typedef ShaderStorage::Header20 Header20; - typedef ShaderStorage::Header19 Header19; - typedef ShaderStorage::Header18 Header18; - - static bool Upgrade_19_To_20(AssetMigrationContext& context) - { - ASSERT(context.Input.SerializedVersion == 19 && context.Output.SerializedVersion == 20); - - // Convert header - if (context.Input.CustomData.IsInvalid()) - return true; - auto& oldHeader = *(Header19*)context.Input.CustomData.Get(); - Header20 newHeader; - Platform::MemoryClear(&newHeader, sizeof(newHeader)); - if (context.Input.Header.TypeName == TEXT("FlaxEngine.ParticleEmitter")) - { - newHeader.ParticleEmitter.GraphVersion = oldHeader.ParticleEmitter.GraphVersion; - newHeader.ParticleEmitter.CustomDataSize = oldHeader.ParticleEmitter.CustomDataSize; - } - else if (context.Input.Header.TypeName == TEXT("FlaxEngine.Material")) - { - newHeader.Material.GraphVersion = oldHeader.Material.GraphVersion; - newHeader.Material.Info = oldHeader.Material.Info; - } - else if (context.Input.Header.TypeName == TEXT("FlaxEngine.Shader")) - { - } - else - { - LOG(Warning, "Unknown input asset type."); - return true; - } - context.Output.CustomData.Copy(&newHeader); - - // Copy all chunks - return CopyChunks(context); - } - - static bool Upgrade_18_To_19(AssetMigrationContext& context) - { - ASSERT(context.Input.SerializedVersion == 18 && context.Output.SerializedVersion == 19); - - // Convert header - if (context.Input.CustomData.IsInvalid()) - return true; - auto& oldHeader = *(Header18*)context.Input.CustomData.Get(); - Header19 newHeader; - Platform::MemoryClear(&newHeader, sizeof(newHeader)); - if (context.Input.Header.TypeName == TEXT("FlaxEngine.ParticleEmitter")) - { - newHeader.ParticleEmitter.GraphVersion = oldHeader.MaterialVersion; - newHeader.ParticleEmitter.CustomDataSize = oldHeader.MaterialInfo.MaxTessellationFactor; - } - else if (context.Input.Header.TypeName == TEXT("FlaxEngine.Material")) - { - newHeader.Material.GraphVersion = oldHeader.MaterialVersion; - newHeader.Material.Info = oldHeader.MaterialInfo; - } - else if (context.Input.Header.TypeName == TEXT("FlaxEngine.Shader")) - { - } - else - { - LOG(Warning, "Unknown input asset type."); - return true; - } - context.Output.CustomData.Copy(&newHeader); - - // Copy all chunks - return CopyChunks(context); - } }; #endif diff --git a/Source/Engine/Content/Upgraders/SkeletonMaskUpgrader.h b/Source/Engine/Content/Upgraders/SkeletonMaskUpgrader.h index 93d01639c..0c7944b91 100644 --- a/Source/Engine/Content/Upgraders/SkeletonMaskUpgrader.h +++ b/Source/Engine/Content/Upgraders/SkeletonMaskUpgrader.h @@ -5,10 +5,6 @@ #if USE_EDITOR #include "BinaryAssetUpgrader.h" -#include "Engine/Content/Assets/SkinnedModel.h" -#include "Engine/Serialization/MemoryReadStream.h" -#include "Engine/Serialization/MemoryWriteStream.h" -#include "Engine/Threading/Threading.h" /// /// Skeleton Mask asset upgrader. @@ -24,79 +20,10 @@ public: { static const Upgrader upgraders[] = { - { 1, 2, &Upgrade_1_To_2 }, + {}, }; setup(upgraders, ARRAY_COUNT(upgraders)); } - -private: - static bool Upgrade_1_To_2(AssetMigrationContext& context) - { - ASSERT(context.Input.SerializedVersion == 1 && context.Output.SerializedVersion == 2); - - // Load data - AssetReference skeleton; - Array bonesMask; - { - auto dataChunk = context.Input.Header.Chunks[0]; - if (dataChunk == nullptr || dataChunk->IsMissing()) - { - LOG(Warning, "Missing data chunk."); - return true; - } - MemoryReadStream stream(dataChunk->Get(), dataChunk->Size()); - - Guid skeletonId; - stream.Read(skeletonId); - int32 maskCount; - stream.ReadInt32(&maskCount); - bonesMask.Resize(maskCount, false); - if (maskCount > 0) - stream.ReadBytes(bonesMask.Get(), maskCount * sizeof(bool)); - - skeleton = skeletonId; - if (skeleton && skeleton->WaitForLoaded()) - { - LOG(Warning, "Failed to load skeleton to update skeleton mask."); - return true; - } - } - - // Build nodes mask from bones - Array nodesMask; - if (skeleton) - { - ScopeLock lock(skeleton->Locker); - - for (int32 i = 0; i < bonesMask.Count(); i++) - { - if (bonesMask[i]) - { - int32 nodeIndex = skeleton->Skeleton.Bones[i].NodeIndex; - nodesMask.Add(skeleton->Skeleton.Nodes[nodeIndex].Name); - } - } - } - - // Save data - { - if (context.AllocateChunk(0)) - return true; - MemoryWriteStream stream(4096); - - const Guid skeletonId = skeleton.GetID(); - stream.Write(skeletonId); - stream.WriteInt32(nodesMask.Count()); - for (auto& e : nodesMask) - { - stream.WriteString(e, -13); - } - - context.Output.Header.Chunks[0]->Data.Copy(stream.GetHandle(), stream.GetPosition()); - } - - return false; - } }; #endif diff --git a/Source/Engine/Content/Upgraders/SkinnedModelAssetUpgrader.h b/Source/Engine/Content/Upgraders/SkinnedModelAssetUpgrader.h index b7800238c..fdd9e66a5 100644 --- a/Source/Engine/Content/Upgraders/SkinnedModelAssetUpgrader.h +++ b/Source/Engine/Content/Upgraders/SkinnedModelAssetUpgrader.h @@ -5,14 +5,6 @@ #if USE_EDITOR #include "BinaryAssetUpgrader.h" -#include "Engine/Platform/Platform.h" -#include "Engine/Serialization/MemoryReadStream.h" -#include "Engine/Serialization/MemoryWriteStream.h" -#include "Engine/Graphics/Models/Types.h" -#include "Engine/Core/Math/BoundingBox.h" -#include "Engine/Core/Math/BoundingSphere.h" -#include "Engine/Core/Math/Matrix.h" -#include "Engine/Core/Math/Transform.h" /// /// Skinned Model Asset Upgrader @@ -28,635 +20,10 @@ public: { static const Upgrader upgraders[] = { - { 1, 2, &Upgrade_1_To_2 }, // [Deprecated on 28.04.2023, expires on 01.01.2024] - { 2, 3, &Upgrade_2_To_3 }, // [Deprecated on 28.04.2023, expires on 01.01.2024] - { 3, 4, &Upgrade_3_To_4 }, // [Deprecated on 28.04.2023, expires on 01.01.2024] - { 4, 5, &Upgrade_4_To_5 }, // [Deprecated on 28.04.2023, expires on 28.04.2026] + {}, }; setup(upgraders, ARRAY_COUNT(upgraders)); } - -private: - static bool Upgrade_1_To_2(AssetMigrationContext& context) - { - ASSERT(context.Input.SerializedVersion == 1 && context.Output.SerializedVersion == 2); - - // Copy header chunk (header format is the same) - if (CopyChunk(context, 0)) - return true; - - // Get mesh data chunk - const auto srcData = context.Input.Header.Chunks[1]; - if (srcData == nullptr || srcData->IsMissing()) - { - LOG(Warning, "Missing model data chunk"); - return true; - } - - // Upgrade meshes data - MemoryReadStream stream(srcData->Get(), srcData->Size()); - MemoryWriteStream output(srcData->Size()); - do - { - uint32 vertices; - stream.ReadUint32(&vertices); - uint32 triangles; - stream.ReadUint32(&triangles); - const uint32 indicesCount = triangles * 3; - const bool use16BitIndexBuffer = indicesCount <= MAX_uint16; - const uint32 ibStride = use16BitIndexBuffer ? sizeof(uint16) : sizeof(uint32); - if (vertices == 0 || triangles == 0) - return true; - const auto vb0 = stream.Move(vertices); - const auto ib = stream.Move(indicesCount * ibStride); - - // Write back - output.WriteUint32(vertices); - output.WriteUint32(triangles); - for (uint32 i = 0; i < vertices; i++) - { - const VB0SkinnedElementType1 oldVertex = vb0[i]; - VB0SkinnedElementType2 newVertex; - newVertex.Position = oldVertex.Position; - newVertex.TexCoord = oldVertex.TexCoord; - newVertex.Normal = oldVertex.Normal; - newVertex.Tangent = oldVertex.Tangent; - newVertex.BlendIndices = oldVertex.BlendIndices; - Float4 blendWeights(oldVertex.BlendWeights.R / 255.0f, oldVertex.BlendWeights.G / 255.0f, oldVertex.BlendWeights.B / 255.0f, oldVertex.BlendWeights.A / 255.0f); - const float sum = blendWeights.SumValues(); - const float invSum = sum > ZeroTolerance ? 1.0f / sum : 0.0f; - blendWeights *= invSum; - newVertex.BlendWeights = Half4(blendWeights); - output.WriteBytes(&newVertex, sizeof(newVertex)); - } - output.WriteBytes(ib, indicesCount * ibStride); - } while (stream.CanRead()); - - // Save new data - if (context.AllocateChunk(1)) - return true; - context.Output.Header.Chunks[1]->Data.Copy(output.GetHandle(), output.GetPosition()); - - return false; - } - - static bool Upgrade_2_To_3(AssetMigrationContext& context) - { - ASSERT(context.Input.SerializedVersion == 2 && context.Output.SerializedVersion == 3); - - // Copy meshes data chunk (format is the same) - if (CopyChunk(context, 1)) - return true; - - // Rewrite header chunk (added LOD count) - const auto srcData = context.Input.Header.Chunks[0]; - if (srcData == nullptr || srcData->IsMissing()) - { - LOG(Warning, "Missing model header chunk"); - return true; - } - MemoryReadStream stream(srcData->Get(), srcData->Size()); - MemoryWriteStream output(srcData->Size()); - { - // Min Screen Size - float minScreenSize; - stream.ReadFloat(&minScreenSize); - output.WriteFloat(minScreenSize); - - // Amount of material slots - int32 materialSlotsCount; - stream.ReadInt32(&materialSlotsCount); - output.WriteInt32(materialSlotsCount); - - // For each material slot - for (int32 materialSlotIndex = 0; materialSlotIndex < materialSlotsCount; materialSlotIndex++) - { - // Material - Guid materialId; - stream.Read(materialId); - output.Write(materialId); - - // Shadows Mode - output.WriteByte(stream.ReadByte()); - - // Name - String name; - stream.ReadString(&name, 11); - output.WriteString(name, 11); - } - - // Amount of LODs - output.WriteByte(1); - - // Screen Size - output.WriteFloat(1.0f); - - // Amount of meshes - uint16 meshesCount; - stream.ReadUint16(&meshesCount); - output.WriteUint16(meshesCount); - - // For each mesh - for (uint16 meshIndex = 0; meshIndex < meshesCount; meshIndex++) - { - // Material Slot index - int32 materialSlotIndex; - stream.ReadInt32(&materialSlotIndex); - output.WriteInt32(materialSlotIndex); - - // Box - BoundingBox box; - stream.Read(box); - output.Write(box); - - // Sphere - BoundingSphere sphere; - stream.Read(sphere); - output.Write(sphere); - } - - // Skeleton - { - int32 nodesCount; - stream.ReadInt32(&nodesCount); - output.WriteInt32(nodesCount); - - // For each node - for (int32 nodeIndex = 0; nodeIndex < nodesCount; nodeIndex++) - { - int32 parentIndex; - stream.ReadInt32(&parentIndex); - output.WriteInt32(parentIndex); - - Transform localTransform; - stream.Read(localTransform); - output.Write(localTransform); - - String name; - stream.ReadString(&name, 71); - output.WriteString(name, 71); - } - - int32 bonesCount; - stream.ReadInt32(&bonesCount); - output.WriteInt32(bonesCount); - - // For each bone - for (int32 boneIndex = 0; boneIndex < bonesCount; boneIndex++) - { - int32 parentIndex; - stream.ReadInt32(&parentIndex); - output.WriteInt32(parentIndex); - - int32 nodeIndex; - stream.ReadInt32(&nodeIndex); - output.WriteInt32(nodeIndex); - - Transform localTransform; - stream.Read(localTransform); - output.Write(localTransform); - - Matrix offsetMatrix; - stream.ReadBytes(&offsetMatrix, sizeof(Matrix)); - output.WriteBytes(&offsetMatrix, sizeof(Matrix)); - } - } - } - - // Save new header data - if (context.AllocateChunk(0)) - return true; - context.Output.Header.Chunks[0]->Data.Copy(output.GetHandle(), output.GetPosition()); - - return false; - } - - static bool Upgrade_3_To_4(AssetMigrationContext& context) - { - ASSERT(context.Input.SerializedVersion == 3 && context.Output.SerializedVersion == 4); - - // Rewrite header chunk (added blend shapes count) - byte lodCount; - Array meshesCounts; - { - const auto srcData = context.Input.Header.Chunks[0]; - if (srcData == nullptr || srcData->IsMissing()) - { - LOG(Warning, "Missing model header chunk"); - return true; - } - MemoryReadStream stream(srcData->Get(), srcData->Size()); - MemoryWriteStream output(srcData->Size()); - - // Min Screen Size - float minScreenSize; - stream.ReadFloat(&minScreenSize); - output.WriteFloat(minScreenSize); - - // Amount of material slots - int32 materialSlotsCount; - stream.ReadInt32(&materialSlotsCount); - output.WriteInt32(materialSlotsCount); - - // For each material slot - for (int32 materialSlotIndex = 0; materialSlotIndex < materialSlotsCount; materialSlotIndex++) - { - // Material - Guid materialId; - stream.Read(materialId); - output.Write(materialId); - - // Shadows Mode - output.WriteByte(stream.ReadByte()); - - // Name - String name; - stream.ReadString(&name, 11); - output.WriteString(name, 11); - } - - // Amount of LODs - stream.ReadByte(&lodCount); - output.WriteByte(lodCount); - meshesCounts.Resize(lodCount); - - // For each LOD - for (int32 lodIndex = 0; lodIndex < lodCount; lodIndex++) - { - // Screen Size - float screenSize; - stream.ReadFloat(&screenSize); - output.WriteFloat(screenSize); - - // Amount of meshes - uint16 meshesCount; - stream.ReadUint16(&meshesCount); - output.WriteUint16(meshesCount); - meshesCounts[lodIndex] = meshesCount; - - // For each mesh - for (uint16 meshIndex = 0; meshIndex < meshesCount; meshIndex++) - { - // Material Slot index - int32 materialSlotIndex; - stream.ReadInt32(&materialSlotIndex); - output.WriteInt32(materialSlotIndex); - - // Box - BoundingBox box; - stream.Read(box); - output.Write(box); - - // Sphere - BoundingSphere sphere; - stream.Read(sphere); - output.Write(sphere); - - // Blend Shapes - output.WriteUint16(0); - } - } - - // Skeleton - { - int32 nodesCount; - stream.ReadInt32(&nodesCount); - output.WriteInt32(nodesCount); - - // For each node - for (int32 nodeIndex = 0; nodeIndex < nodesCount; nodeIndex++) - { - int32 parentIndex; - stream.ReadInt32(&parentIndex); - output.WriteInt32(parentIndex); - - Transform localTransform; - stream.Read(localTransform); - output.Write(localTransform); - - String name; - stream.ReadString(&name, 71); - output.WriteString(name, 71); - } - - int32 bonesCount; - stream.ReadInt32(&bonesCount); - output.WriteInt32(bonesCount); - - // For each bone - for (int32 boneIndex = 0; boneIndex < bonesCount; boneIndex++) - { - int32 parentIndex; - stream.ReadInt32(&parentIndex); - output.WriteInt32(parentIndex); - - int32 nodeIndex; - stream.ReadInt32(&nodeIndex); - output.WriteInt32(nodeIndex); - - Transform localTransform; - stream.Read(localTransform); - output.Write(localTransform); - - Matrix offsetMatrix; - stream.ReadBytes(&offsetMatrix, sizeof(Matrix)); - output.WriteBytes(&offsetMatrix, sizeof(Matrix)); - } - } - - // Save new data - if (stream.GetPosition() != stream.GetLength()) - { - LOG(Error, "Invalid position after upgrading skinned model header data."); - return true; - } - if (context.AllocateChunk(0)) - return true; - context.Output.Header.Chunks[0]->Data.Copy(output.GetHandle(), output.GetPosition()); - } - - // Rewrite meshes data chunks (blend shapes added) - for (int32 lodIndex = 0; lodIndex < lodCount; lodIndex++) - { - const int32 chunkIndex = lodIndex + 1; - const auto srcData = context.Input.Header.Chunks[chunkIndex]; - if (srcData == nullptr || srcData->IsMissing()) - { - LOG(Warning, "Missing skinned model LOD meshes data chunk"); - return true; - } - MemoryReadStream stream(srcData->Get(), srcData->Size()); - MemoryWriteStream output(srcData->Size()); - - for (int32 meshIndex = 0; meshIndex < meshesCounts[lodIndex]; meshIndex++) - { - uint32 vertices; - stream.ReadUint32(&vertices); - output.WriteUint32(vertices); - uint32 triangles; - stream.ReadUint32(&triangles); - output.WriteUint32(triangles); - uint16 blendShapesCount = 0; - output.WriteUint16(blendShapesCount); - const uint32 indicesCount = triangles * 3; - const bool use16BitIndexBuffer = indicesCount <= MAX_uint16; - const uint32 ibStride = use16BitIndexBuffer ? sizeof(uint16) : sizeof(uint32); - if (vertices == 0 || triangles == 0) - return true; - const auto vb0 = stream.Move(vertices); - output.WriteBytes(vb0, vertices * sizeof(VB0SkinnedElementType)); - const auto ib = stream.Move(indicesCount * ibStride); - output.WriteBytes(ib, indicesCount * ibStride); - } - - // Save new data - if (stream.GetPosition() != stream.GetLength()) - { - LOG(Error, "Invalid position after upgrading skinned model LOD meshes data."); - return true; - } - if (context.AllocateChunk(chunkIndex)) - return true; - context.Output.Header.Chunks[chunkIndex]->Data.Copy(output.GetHandle(), output.GetPosition()); - } - - return false; - } - - static bool Upgrade_4_To_5(AssetMigrationContext& context) - { - ASSERT(context.Input.SerializedVersion == 4 && context.Output.SerializedVersion == 5); - - // Changes: - // - added version number to header (for easier changes in future) - // - added version number to mesh data (for easier changes in future) - // - added skeleton retarget setups to header - - // Rewrite header chunk (added header version and retarget entries) - byte lodCount; - Array meshesCounts; - { - const auto srcData = context.Input.Header.Chunks[0]; - if (srcData == nullptr || srcData->IsMissing()) - { - LOG(Warning, "Missing model header chunk"); - return true; - } - MemoryReadStream stream(srcData->Get(), srcData->Size()); - MemoryWriteStream output(srcData->Size()); - - // Header Version - output.WriteByte(1); - - // Min Screen Size - float minScreenSize; - stream.ReadFloat(&minScreenSize); - output.WriteFloat(minScreenSize); - - // Amount of material slots - int32 materialSlotsCount; - stream.ReadInt32(&materialSlotsCount); - output.WriteInt32(materialSlotsCount); - - // For each material slot - for (int32 materialSlotIndex = 0; materialSlotIndex < materialSlotsCount; materialSlotIndex++) - { - // Material - Guid materialId; - stream.Read(materialId); - output.Write(materialId); - - // Shadows Mode - output.WriteByte(stream.ReadByte()); - - // Name - String name; - stream.ReadString(&name, 11); - output.WriteString(name, 11); - } - - // Amount of LODs - stream.ReadByte(&lodCount); - output.WriteByte(lodCount); - meshesCounts.Resize(lodCount); - - // For each LOD - for (int32 lodIndex = 0; lodIndex < lodCount; lodIndex++) - { - // Screen Size - float screenSize; - stream.ReadFloat(&screenSize); - output.WriteFloat(screenSize); - - // Amount of meshes - uint16 meshesCount; - stream.ReadUint16(&meshesCount); - output.WriteUint16(meshesCount); - meshesCounts[lodIndex] = meshesCount; - - // For each mesh - for (uint16 meshIndex = 0; meshIndex < meshesCount; meshIndex++) - { - // Material Slot index - int32 materialSlotIndex; - stream.ReadInt32(&materialSlotIndex); - output.WriteInt32(materialSlotIndex); - - // Box - BoundingBox box; - stream.Read(box); - output.Write(box); - - // Sphere - BoundingSphere sphere; - stream.Read(sphere); - output.Write(sphere); - - // Blend Shapes - uint16 blendShapes; - stream.ReadUint16(&blendShapes); - output.WriteUint16(blendShapes); - for (int32 blendShapeIndex = 0; blendShapeIndex < blendShapes; blendShapeIndex++) - { - String blendShapeName; - stream.ReadString(&blendShapeName, 13); - output.WriteString(blendShapeName, 13); - float blendShapeWeight; - stream.ReadFloat(&blendShapeWeight); - output.WriteFloat(blendShapeWeight); - } - } - } - - // Skeleton - { - int32 nodesCount; - stream.ReadInt32(&nodesCount); - output.WriteInt32(nodesCount); - - // For each node - for (int32 nodeIndex = 0; nodeIndex < nodesCount; nodeIndex++) - { - int32 parentIndex; - stream.ReadInt32(&parentIndex); - output.WriteInt32(parentIndex); - - Transform localTransform; - stream.Read(localTransform); - output.Write(localTransform); - - String name; - stream.ReadString(&name, 71); - output.WriteString(name, 71); - } - - int32 bonesCount; - stream.ReadInt32(&bonesCount); - output.WriteInt32(bonesCount); - - // For each bone - for (int32 boneIndex = 0; boneIndex < bonesCount; boneIndex++) - { - int32 parentIndex; - stream.ReadInt32(&parentIndex); - output.WriteInt32(parentIndex); - - int32 nodeIndex; - stream.ReadInt32(&nodeIndex); - output.WriteInt32(nodeIndex); - - Transform localTransform; - stream.Read(localTransform); - output.Write(localTransform); - - Matrix offsetMatrix; - stream.ReadBytes(&offsetMatrix, sizeof(Matrix)); - output.WriteBytes(&offsetMatrix, sizeof(Matrix)); - } - } - - // Retargeting - { - output.WriteInt32(0); - } - - // Save new data - if (stream.GetPosition() != stream.GetLength()) - { - LOG(Error, "Invalid position after upgrading skinned model header data."); - return true; - } - if (context.AllocateChunk(0)) - return true; - context.Output.Header.Chunks[0]->Data.Copy(output.GetHandle(), output.GetPosition()); - } - - // Rewrite meshes data chunks - for (int32 lodIndex = 0; lodIndex < lodCount; lodIndex++) - { - const int32 chunkIndex = lodIndex + 1; - const auto srcData = context.Input.Header.Chunks[chunkIndex]; - if (srcData == nullptr || srcData->IsMissing()) - { - LOG(Warning, "Missing skinned model LOD meshes data chunk"); - return true; - } - MemoryReadStream stream(srcData->Get(), srcData->Size()); - MemoryWriteStream output(srcData->Size()); - - // Mesh Data Version - output.WriteByte(1); - - for (int32 meshIndex = 0; meshIndex < meshesCounts[lodIndex]; meshIndex++) - { - uint32 vertices; - stream.ReadUint32(&vertices); - output.WriteUint32(vertices); - uint32 triangles; - stream.ReadUint32(&triangles); - output.WriteUint32(triangles); - uint16 blendShapesCount; - stream.ReadUint16(&blendShapesCount); - output.WriteUint16(blendShapesCount); - for (int32 blendShapeIndex = 0; blendShapeIndex < blendShapesCount; blendShapeIndex++) - { - output.WriteBool(stream.ReadBool()); - uint32 minVertexIndex, maxVertexIndex; - stream.ReadUint32(&minVertexIndex); - output.WriteUint32(minVertexIndex); - stream.ReadUint32(&maxVertexIndex); - output.WriteUint32(maxVertexIndex); - uint32 blendShapeVertices; - stream.ReadUint32(&blendShapeVertices); - output.WriteUint32(blendShapeVertices); - const uint32 blendShapeDataSize = blendShapeVertices * sizeof(BlendShapeVertex); - const auto blendShapeData = stream.Move(blendShapeDataSize); - output.WriteBytes(blendShapeData, blendShapeDataSize); - } - const uint32 indicesCount = triangles * 3; - const bool use16BitIndexBuffer = indicesCount <= MAX_uint16; - const uint32 ibStride = use16BitIndexBuffer ? sizeof(uint16) : sizeof(uint32); - if (vertices == 0 || triangles == 0) - return true; - const auto vb0 = stream.Move(vertices); - output.WriteBytes(vb0, vertices * sizeof(VB0SkinnedElementType)); - const auto ib = stream.Move(indicesCount * ibStride); - output.WriteBytes(ib, indicesCount * ibStride); - } - - // Save new data - if (stream.GetPosition() != stream.GetLength()) - { - LOG(Error, "Invalid position after upgrading skinned model LOD meshes data."); - return true; - } - if (context.AllocateChunk(chunkIndex)) - return true; - context.Output.Header.Chunks[chunkIndex]->Data.Copy(output.GetHandle(), output.GetPosition()); - } - - return false; - } }; #endif diff --git a/Source/Engine/Content/Upgraders/TextureAssetUpgrader.h b/Source/Engine/Content/Upgraders/TextureAssetUpgrader.h index 53b224b79..efe5c6547 100644 --- a/Source/Engine/Content/Upgraders/TextureAssetUpgrader.h +++ b/Source/Engine/Content/Upgraders/TextureAssetUpgrader.h @@ -5,19 +5,6 @@ #if USE_EDITOR #include "BinaryAssetUpgrader.h" -#include "Engine/Core/Core.h" -#include "Engine/Platform/Platform.h" -#include "Engine/Graphics/RenderTools.h" -#include "Engine/Content/Assets/CubeTexture.h" -#include "Engine/Content/Assets/IESProfile.h" -#include "Engine/Content/Assets/Texture.h" -#include "Engine/Utilities/Encryption.h" -#include "Engine/Serialization/JsonTools.h" -#include "Engine/Serialization/MemoryReadStream.h" -#include "Engine/Render2D/SpriteAtlas.h" -#if USE_EDITOR -#include "Editor/Content/PreviewsCache.h" -#endif /// /// Texture Asset Upgrader @@ -33,792 +20,10 @@ public: { static const Upgrader upgraders[] = { - { 1, 4, &Upgrade_1_To_4 }, + {}, }; setup(upgraders, ARRAY_COUNT(upgraders)); } - -private: - // ============================================ - // Versions 1, 2 and 3: - // Designed: long time ago in a galaxy far far away - // Custom Data: not used - // Chunk 0: Header (sprite atlas also stored sprites) - // Chunk 1-14: Texture Mips - // Chunk 15: Texture Import options - // ============================================ - // - // Note: we merge CubeTexture, Texture, AssetPreviewsCache, IESProfile and AssetSpriteAtlas storage backend. - // This simplifies textures operations like importing/exporting and allows to reduce amount of code to maintain. - // - // Firstly store texture header inside a CustomData field and get it just after asset creation. - // Secondly move texture import metadata (format, max size, etc.) to the json metadata. - // Lastly store all texture mips in chunks 1-14 and use 15th and 16th chunk for custom data per asset type (sprites or thumbnails meta, etc.). - // Note: mips order has been changed, Chunk[0..13] contain now Mip[0..13]. Internal storage layer should manage data chunks order inside a file, not an asset. - // Additionally texture header contains a few bytes to be used by the assets (for eg. IES Profile uses it to store Brightness parameter) - // - // Old AssetPreviewsCache: - // Chunk 0: header - // Chunk 1: assets ID table - // Chunk 2: atlas image - // ============================================ - // Version 4: - // Designed: 4/25/2017 - // Custom Data: Header - // Metadata: Import Options - // Chunk 0-13: Mips (from the highest quality to the lowest) - // Chunk 15: Custom Asset Data: - // - AssetSpriteAtlas: sprites - // - AssetPreviewsCache: asset previews meta - // ============================================ - - enum class PixelFormatOld - { - PF_Unknown = 0, - PF_R8G8B8A8 = 1, - PF_R16G16B16A16 = 2, - PF_R32G32B32A32 = 3, - PF_A8 = 4, - PF_R16F = 5, - PF_R32 = 6, - PF_R16G16 = 7, - PF_R32G32 = 8, - PF_R10G10B10A2 = 9, - PF_R11G11B10 = 10, - PF_BC1 = 11, - PF_BC2 = 12, - PF_BC3 = 13, - PF_BC4 = 14, - PF_BC5 = 15, - PF_B8G8R8A8 = 16, - PF_DepthStencil = 17, - PF_ShadowDepth = 18, - PF_D16 = 19, - PF_D24 = 20, - PF_D32 = 21, - PF_R16 = 22, - PF_B5G6R5 = 23, - PF_R8G8_SNORM = 24, - PF_R8G8_UNORM = 25, - }; - - static PixelFormat PixelFormatOldToNew(PixelFormatOld format) - { - switch (format) - { - case PixelFormatOld::PF_Unknown: - return PixelFormat::Unknown; - case PixelFormatOld::PF_R8G8B8A8: - return PixelFormat::R8G8B8A8_UNorm; - case PixelFormatOld::PF_R16G16B16A16: - return PixelFormat::R16G16B16A16_Float; - case PixelFormatOld::PF_R32G32B32A32: - return PixelFormat::R32G32B32A32_Float; - case PixelFormatOld::PF_A8: - return PixelFormat::A8_UNorm; - case PixelFormatOld::PF_R16F: - return PixelFormat::R16_Float; - case PixelFormatOld::PF_R32: - return PixelFormat::R32_Float; - case PixelFormatOld::PF_R16G16: - return PixelFormat::R16G16_Float; - case PixelFormatOld::PF_R32G32: - return PixelFormat::R32G32_Float; - case PixelFormatOld::PF_R10G10B10A2: - return PixelFormat::R10G10B10A2_UNorm; - case PixelFormatOld::PF_R11G11B10: - return PixelFormat::R11G11B10_Float; - case PixelFormatOld::PF_BC1: - return PixelFormat::BC1_UNorm; - case PixelFormatOld::PF_BC2: - return PixelFormat::BC2_UNorm; - case PixelFormatOld::PF_BC3: - return PixelFormat::BC3_UNorm; - case PixelFormatOld::PF_BC4: - return PixelFormat::BC4_UNorm; - case PixelFormatOld::PF_BC5: - return PixelFormat::BC5_UNorm; - case PixelFormatOld::PF_B8G8R8A8: - return PixelFormat::B8G8R8A8_UNorm; - case PixelFormatOld::PF_DepthStencil: - return PixelFormat::D24_UNorm_S8_UInt; - case PixelFormatOld::PF_ShadowDepth: - return PixelFormat::D32_Float; - case PixelFormatOld::PF_D16: - return PixelFormat::D16_UNorm; - case PixelFormatOld::PF_D24: - return PixelFormat::D24_UNorm_S8_UInt; - case PixelFormatOld::PF_D32: - return PixelFormat::D32_Float; - case PixelFormatOld::PF_R16: - return PixelFormat::R16_UNorm; - case PixelFormatOld::PF_B5G6R5: - return PixelFormat::B5G6R5_UNorm; - case PixelFormatOld::PF_R8G8_SNORM: - return PixelFormat::R8G8_SNorm; - case PixelFormatOld::PF_R8G8_UNORM: - return PixelFormat::R8G8_UNorm; - default: ; - } - - CRASH; - return PixelFormat::Unknown; - } - - static PixelFormatOld PixelFormatToOld(PixelFormat format) - { - switch (format) - { - case PixelFormat::Unknown: - return PixelFormatOld::PF_Unknown; - case PixelFormat::R32G32B32A32_Typeless: - case PixelFormat::R32G32B32A32_Float: - case PixelFormat::R32G32B32A32_UInt: - case PixelFormat::R32G32B32A32_SInt: - return PixelFormatOld::PF_R32G32B32A32; - //case PixelFormat::R32G32B32_Typeless: - //case PixelFormat::R32G32B32_Float: - //case PixelFormat::R32G32B32_UInt: - //case PixelFormat::R32G32B32_SInt: - case PixelFormat::R16G16B16A16_Typeless: - case PixelFormat::R16G16B16A16_Float: - case PixelFormat::R16G16B16A16_UNorm: - case PixelFormat::R16G16B16A16_UInt: - case PixelFormat::R16G16B16A16_SNorm: - case PixelFormat::R16G16B16A16_SInt: - return PixelFormatOld::PF_R16G16B16A16; - case PixelFormat::R32G32_Typeless: - case PixelFormat::R32G32_Float: - case PixelFormat::R32G32_UInt: - case PixelFormat::R32G32_SInt: - case PixelFormat::R32G8X24_Typeless: - return PixelFormatOld::PF_R32G32; - case PixelFormat::D32_Float_S8X24_UInt: - case PixelFormat::R32_Float_X8X24_Typeless: - case PixelFormat::X32_Typeless_G8X24_UInt: - return PixelFormatOld::PF_R32G32B32A32; - case PixelFormat::R10G10B10A2_Typeless: - case PixelFormat::R10G10B10A2_UNorm: - case PixelFormat::R10G10B10A2_UInt: - return PixelFormatOld::PF_R10G10B10A2; - case PixelFormat::R11G11B10_Float: - return PixelFormatOld::PF_R11G11B10; - case PixelFormat::R8G8B8A8_Typeless: - case PixelFormat::R8G8B8A8_UNorm: - case PixelFormat::R8G8B8A8_UNorm_sRGB: - case PixelFormat::R8G8B8A8_UInt: - case PixelFormat::R8G8B8A8_SNorm: - case PixelFormat::R8G8B8A8_SInt: - return PixelFormatOld::PF_R8G8B8A8; - case PixelFormat::R16G16_Typeless: - case PixelFormat::R16G16_Float: - case PixelFormat::R16G16_UNorm: - case PixelFormat::R16G16_UInt: - case PixelFormat::R16G16_SNorm: - case PixelFormat::R16G16_SInt: - return PixelFormatOld::PF_R16G16; - case PixelFormat::R32_Typeless: - return PixelFormatOld::PF_R32; - case PixelFormat::D32_Float: - return PixelFormatOld::PF_DepthStencil; - case PixelFormat::R32_Float: - case PixelFormat::R32_UInt: - case PixelFormat::R32_SInt: - return PixelFormatOld::PF_R32; - case PixelFormat::R24G8_Typeless: - case PixelFormat::D24_UNorm_S8_UInt: - case PixelFormat::R24_UNorm_X8_Typeless: - return PixelFormatOld::PF_DepthStencil; - //case PixelFormat::X24_Typeless_G8_UInt: - case PixelFormat::R8G8_Typeless: - case PixelFormat::R8G8_UNorm: - case PixelFormat::R8G8_UInt: - return PixelFormatOld::PF_R8G8_UNORM; - case PixelFormat::R8G8_SNorm: - case PixelFormat::R8G8_SInt: - return PixelFormatOld::PF_R8G8_SNORM; - case PixelFormat::R16_Float: - return PixelFormatOld::PF_R16F; - case PixelFormat::R16_Typeless: - case PixelFormat::D16_UNorm: - case PixelFormat::R16_UNorm: - case PixelFormat::R16_UInt: - case PixelFormat::R16_SNorm: - case PixelFormat::R16_SInt: - return PixelFormatOld::PF_R16; - case PixelFormat::R8_Typeless: - case PixelFormat::R8_UNorm: - case PixelFormat::R8_UInt: - case PixelFormat::R8_SNorm: - case PixelFormat::R8_SInt: - case PixelFormat::A8_UNorm: - return PixelFormatOld::PF_A8; - case PixelFormat::R1_UNorm: - //case PixelFormat::R9G9B9E5_Sharedexp: - //case PixelFormat::R8G8_B8G8_UNorm: - //case PixelFormat::G8R8_G8B8_UNorm: - case PixelFormat::BC1_Typeless: - case PixelFormat::BC1_UNorm: - case PixelFormat::BC1_UNorm_sRGB: - return PixelFormatOld::PF_BC1; - case PixelFormat::BC2_Typeless: - case PixelFormat::BC2_UNorm: - case PixelFormat::BC2_UNorm_sRGB: - return PixelFormatOld::PF_BC2; - case PixelFormat::BC3_Typeless: - case PixelFormat::BC3_UNorm: - case PixelFormat::BC3_UNorm_sRGB: - return PixelFormatOld::PF_BC3; - case PixelFormat::BC4_Typeless: - case PixelFormat::BC4_UNorm: - case PixelFormat::BC4_SNorm: - return PixelFormatOld::PF_BC4; - case PixelFormat::BC5_Typeless: - case PixelFormat::BC5_UNorm: - case PixelFormat::BC5_SNorm: - return PixelFormatOld::PF_BC5; - case PixelFormat::B5G6R5_UNorm: - return PixelFormatOld::PF_B5G6R5; - //case PixelFormat::B5G5R5A1_UNorm: - //case PixelFormat::B8G8R8A8_UNorm: - //case PixelFormat::B8G8R8X8_UNorm: - //case PixelFormat::R10G10B10_Xr_Bias_A2_UNorm: - //case PixelFormat::B8G8R8A8_Typeless: - //case PixelFormat::B8G8R8A8_UNorm_sRGB: - //case PixelFormat::B8G8R8X8_Typeless: - //case PixelFormat::B8G8R8X8_UNorm_sRGB: - //case PixelFormat::BC6H_Typeless: - //case PixelFormat::BC6H_Uf16: - //case PixelFormat::BC6H_Sf16: - //case PixelFormat::BC7_Typeless: - //case PixelFormat::BC7_UNorm: - //case PixelFormat::BC7_UNorm_sRGB: - default: - break; - } - - CRASH; - return PixelFormatOld::PF_Unknown; - } - - struct TextureHeader1 - { - int32 Width; - int32 Height; - byte MipLevels; - bool NeverStream; - TextureFormatType Type; - PixelFormatOld Format; - bool IsSRGB; - }; - - struct TextureHeader2 - { - int32 Width; - int32 Height; - byte MipLevels; - bool NeverStream; - TextureFormatType Type; - PixelFormatOld Format; - bool IsSRGB; - }; - - struct TextureHeader3 - { - int32 Width; - int32 Height; - int32 MipLevels; - bool IsCubeMap; - bool NeverStream; - TextureFormatType Type; - PixelFormat Format; - bool IsSRGB; - }; - - struct CubeTextureHeader1 - { - int32 Size; - byte MipLevels; - PixelFormatOld Format; - bool IsSRGB; - }; - - enum class TextureOwnerType1 - { - Texture, - CubeTexture, - SpriteAtlas, - IESProfile, - PreviewsCache, - }; - - static bool GetOwnerType(AssetMigrationContext& context, TextureOwnerType1& type) - { - auto typeName = context.Input.Header.TypeName; - - if (typeName == Texture::TypeName) - { - type = TextureOwnerType1::Texture; - return false; - } - if (typeName == CubeTexture::TypeName) - { - type = TextureOwnerType1::CubeTexture; - return false; - } - if (typeName == SpriteAtlas::TypeName) - { - type = TextureOwnerType1::SpriteAtlas; - return false; - } - if (typeName == IESProfile::TypeName) - { - type = TextureOwnerType1::IESProfile; - return false; - } -#if USE_EDITOR - if (typeName == PreviewsCache::TypeName) - { - type = TextureOwnerType1::PreviewsCache; - return false; - } -#endif - - LOG(Warning, "Invalid input asset type."); - return true; - } - - static bool Upgrade_1_To_4_ImportOptions(AssetMigrationContext& context) - { - // Check if has no 15th chunk - auto chunk = context.Input.Header.Chunks[15]; - if (chunk == nullptr || chunk->IsMissing()) - return false; - -#if USE_EDITOR - - // Get import metadata json - rapidjson_flax::Document importMeta; - if (context.Input.Metadata.IsValid()) - { - importMeta.Parse((const char*)context.Input.Metadata.Get(), context.Input.Metadata.Length()); - if (importMeta.HasParseError()) - { - LOG(Warning, "Failed to parse import meta json."); - return true; - } - } - - // Get import options json - rapidjson_flax::Document importOptions; - { - // Decrypt bytes - int32 length = chunk->Size(); - Encryption::DecryptBytes(chunk->Get(), length); - - // Load Json - static_assert(sizeof(char) == sizeof(rapidjson_flax::Document::Ch), "Invalid rapidJson document char size."); - int32 tmpJsonSize = length; - importOptions.Parse((const char*)chunk->Get(), tmpJsonSize); - if (importOptions.HasParseError()) - { - LOG(Warning, "Failed to parse import options json."); - return true; - } - } - - // Merge deprecated json meta from chunk 15 with import metadata - JsonTools::MergeDocuments(importMeta, importOptions); - - // Save json metadata - { - rapidjson_flax::StringBuffer buffer; - rapidjson_flax::Writer writer(buffer); - if (!importMeta.Accept(writer)) - { - LOG(Warning, "Failed to serialize metadata json."); - return true; - } - context.Output.Metadata.Copy((const byte*)buffer.GetString(), (uint32)buffer.GetSize()); - } - -#endif - - return false; - } - - static bool Upgrade_1_To_4_Texture(AssetMigrationContext& context) - { - // Get texture header - auto headerChunk = context.Input.Header.Chunks[0]; - if (headerChunk == nullptr || headerChunk->IsMissing()) - { - LOG(Warning, "Missing texture header chunk."); - return true; - } - MemoryReadStream headerStream(headerChunk->Get(), headerChunk->Size()); - - // Load texture header - int32 textureHeaderVersion; - headerStream.ReadInt32(&textureHeaderVersion); - if (textureHeaderVersion != 1) - { - LOG(Warning, "Invalid texture header version."); - return true; - } - TextureHeader1 textureHeader; - headerStream.ReadBytes(&textureHeader, sizeof(textureHeader)); - - // Create new header - TextureHeader newHeader; - newHeader.Width = textureHeader.Width; - newHeader.Height = textureHeader.Height; - newHeader.MipLevels = textureHeader.MipLevels; - newHeader.Format = PixelFormatOldToNew(textureHeader.Format); - newHeader.IsSRGB = textureHeader.IsSRGB; - newHeader.NeverStream = textureHeader.NeverStream; - newHeader.Type = textureHeader.Type; - context.Output.CustomData.Copy(&newHeader); - - // Convert import options - if (Upgrade_1_To_4_ImportOptions(context)) - return true; - - // Copy mip maps - for (int32 mipIndex = 0; mipIndex < newHeader.MipLevels; mipIndex++) - { - auto srcChunk = context.Input.Header.Chunks[newHeader.MipLevels - mipIndex]; - if (srcChunk == nullptr || srcChunk->IsMissing()) - { - LOG(Warning, "Missing data chunk with a mipmap"); - return true; - } - if (context.AllocateChunk(mipIndex)) - return true; - auto dstChunk = context.Output.Header.Chunks[mipIndex]; - - dstChunk->Data.Copy(srcChunk->Data); - } - - return false; - } - - static bool Upgrade_1_To_4_CubeTexture(AssetMigrationContext& context) - { - // Get texture header - auto headerChunk = context.Input.Header.Chunks[0]; - if (headerChunk == nullptr || headerChunk->IsMissing()) - { - LOG(Warning, "Missing cube texture header chunk."); - return true; - } - MemoryReadStream headerStream(headerChunk->Get(), headerChunk->Size()); - - // Load texture header - int32 textureHeaderVersion; - headerStream.ReadInt32(&textureHeaderVersion); - if (textureHeaderVersion != 1) - { - LOG(Warning, "Invalid cube texture header version."); - return true; - } - CubeTextureHeader1 textureHeader; - headerStream.ReadBytes(&textureHeader, sizeof(textureHeader)); - - // Create new header - TextureHeader newHeader; - newHeader.Width = textureHeader.Size; - newHeader.Height = textureHeader.Size; - newHeader.MipLevels = textureHeader.MipLevels; - newHeader.Format = PixelFormatOldToNew(textureHeader.Format); - newHeader.IsSRGB = textureHeader.IsSRGB; - newHeader.Type = TextureFormatType::ColorRGB; - newHeader.IsCubeMap = true; - context.Output.CustomData.Copy(&newHeader); - - // Convert import options - if (Upgrade_1_To_4_ImportOptions(context)) - return true; - - // Conversion from single chunk to normal texture chunks mapping mode (single mip per chunk) - { - auto cubeTextureData = context.Input.Header.Chunks[1]; - if (cubeTextureData == nullptr || cubeTextureData->IsMissing()) - { - LOG(Warning, "Missing data chunk with a cubemap"); - return true; - } - uint32 dataSize = cubeTextureData->Size(); - auto data = cubeTextureData->Get(); - - auto mipLevels = textureHeader.MipLevels; - auto textureSize = textureHeader.Size; - ASSERT(mipLevels > 0 && mipLevels <= GPU_MAX_TEXTURE_MIP_LEVELS); - ASSERT(textureSize > 0 && textureSize <= GPU_MAX_TEXTURE_SIZE); - - //Platform::MemorySet(cubeTextureData.Get(), cubeTextureData.Length(), MAX_uint32); - - byte* position = (byte*)data; - for (int32 mipIndex = 0; mipIndex < mipLevels; mipIndex++) - { - uint32 mipSize = textureSize >> mipIndex; - - uint32 rowPitch, slicePitch; - RenderTools::ComputePitch(PixelFormatOldToNew(textureHeader.Format), mipSize, mipSize, rowPitch, slicePitch); - - uint32 mipDataSize = slicePitch * 6; - - // Create mip - if (context.AllocateChunk(mipIndex)) - return true; - auto dstChunk = context.Output.Header.Chunks[mipIndex]; - dstChunk->Data.Copy(position, mipDataSize); - - position += mipDataSize; - } - ASSERT(dataSize == (uint32)(position - data)); - } - - return false; - } - - static bool Upgrade_1_To_4_SpriteAtlas(AssetMigrationContext& context) - { - // Get texture header - auto headerChunk = context.Input.Header.Chunks[0]; - if (headerChunk == nullptr || headerChunk->IsMissing()) - { - LOG(Warning, "Missing texture header chunk."); - return true; - } - MemoryReadStream headerStream(headerChunk->Get(), headerChunk->Size()); - - // Load texture header - int32 textureHeaderVersion; - headerStream.ReadInt32(&textureHeaderVersion); - if (textureHeaderVersion != 1) - { - LOG(Warning, "Invalid texture header version."); - return true; - } - TextureHeader1 textureHeader; - headerStream.ReadBytes(&textureHeader, sizeof(textureHeader)); - - // Create new header - TextureHeader newHeader; - newHeader.Width = textureHeader.Width; - newHeader.Height = textureHeader.Height; - newHeader.MipLevels = textureHeader.MipLevels; - newHeader.Format = PixelFormatOldToNew(textureHeader.Format); - newHeader.IsSRGB = textureHeader.IsSRGB; - newHeader.NeverStream = textureHeader.NeverStream; - newHeader.Type = textureHeader.Type; - context.Output.CustomData.Copy(&newHeader); - - // Copy sprite atlas data from old header stream to chunk (chunk 15th) - if (context.AllocateChunk(15)) - return true; - context.Output.Header.Chunks[15]->Data.Copy(headerStream.GetPositionHandle(), headerStream.GetLength() - headerStream.GetPosition()); - - // Convert import options - if (Upgrade_1_To_4_ImportOptions(context)) - return true; - - // Copy mip maps - for (int32 mipIndex = 0; mipIndex < newHeader.MipLevels; mipIndex++) - { - auto srcChunk = context.Input.Header.Chunks[newHeader.MipLevels - mipIndex]; - if (srcChunk == nullptr || srcChunk->IsMissing()) - { - LOG(Warning, "Missing data chunk with a mipmap"); - return true; - } - if (context.AllocateChunk(mipIndex)) - return true; - auto dstChunk = context.Output.Header.Chunks[mipIndex]; - - dstChunk->Data.Copy(srcChunk->Data); - } - - return false; - } - - static bool Upgrade_1_To_4_IESProfile(AssetMigrationContext& context) - { - // Get texture header - auto headerChunk = context.Input.Header.Chunks[0]; - if (headerChunk == nullptr || headerChunk->IsMissing()) - { - LOG(Warning, "Missing IES profile texture header chunk."); - return true; - } - MemoryReadStream headerStream(headerChunk->Get(), headerChunk->Size()); - - // Load IES header - int32 iesHeaderVersion; - headerStream.ReadInt32(&iesHeaderVersion); - if (iesHeaderVersion != 1) - { - LOG(Warning, "Invalid IES profile header."); - return true; - } - float brightness, multiplier; - headerStream.ReadFloat(&brightness); - headerStream.ReadFloat(&multiplier); - - // Load texture header - int32 textureHeaderVersion; - headerStream.ReadInt32(&textureHeaderVersion); - if (textureHeaderVersion != 1) - { - LOG(Warning, "Invalid texture header version."); - return true; - } - TextureHeader1 textureHeader; - headerStream.ReadBytes(&textureHeader, sizeof(textureHeader)); - if (textureHeader.MipLevels != 1) - { - LOG(Warning, "Invalid IES profile texture header."); - return true; - } - - // Create new header - TextureHeader newHeader; - newHeader.Width = textureHeader.Width; - newHeader.Height = textureHeader.Height; - newHeader.MipLevels = textureHeader.MipLevels; - newHeader.Format = PixelFormatOldToNew(textureHeader.Format); - newHeader.IsSRGB = textureHeader.IsSRGB; - newHeader.NeverStream = textureHeader.NeverStream; - newHeader.Type = textureHeader.Type; - auto data = (IESProfile::CustomDataLayout*)newHeader.CustomData; - data->Brightness = brightness; - data->TextureMultiplier = multiplier; - context.Output.CustomData.Copy(&newHeader); - - // Convert import options - if (Upgrade_1_To_4_ImportOptions(context)) - return true; - - // Copy texture - { - auto srcChunk = context.Input.Header.Chunks[1]; - if (srcChunk == nullptr || srcChunk->IsMissing()) - { - LOG(Warning, "Missing data chunk with a mipmap"); - return true; - } - if (context.AllocateChunk(0)) - return true; - auto dstChunk = context.Output.Header.Chunks[0]; - - dstChunk->Data.Copy(srcChunk->Data); - } - - return false; - } - - static bool Upgrade_1_To_4_PreviewsCache(AssetMigrationContext& context) - { - // Get texture header - auto headerChunk = context.Input.Header.Chunks[0]; - if (headerChunk == nullptr || headerChunk->IsMissing()) - { - LOG(Warning, "Missing texture header chunk."); - return true; - } - MemoryReadStream headerStream(headerChunk->Get(), headerChunk->Size()); - - // Load atlas header - struct AtlasHeader1 - { - int32 Version; - int32 TextureHeaderVersion; - TextureHeader1 TextureHeader; - }; - AtlasHeader1 atlasHeader; - headerStream.ReadBytes(&atlasHeader, sizeof(atlasHeader)); - if (atlasHeader.Version != 1 || atlasHeader.TextureHeaderVersion != 1) - { - LOG(Warning, "Invalid asset previews header."); - return true; - } - auto& textureHeader = atlasHeader.TextureHeader; - if (textureHeader.MipLevels != 1) - { - LOG(Warning, "Invalid asset previews texture header."); - return true; - } - - // Create new header - TextureHeader newHeader; - newHeader.Width = textureHeader.Width; - newHeader.Height = textureHeader.Height; - newHeader.MipLevels = textureHeader.MipLevels; - newHeader.Format = PixelFormatOldToNew(textureHeader.Format); - newHeader.IsSRGB = textureHeader.IsSRGB; - newHeader.NeverStream = textureHeader.NeverStream; - newHeader.Type = textureHeader.Type; - context.Output.CustomData.Copy(&newHeader); - - // Copy asset previews IDs mapping data from old chunk to new one - auto idsChunk = context.Input.Header.Chunks[1]; - if (idsChunk == nullptr || idsChunk->IsMissing()) - { - LOG(Warning, "Missing asset previews IDs mapping data chunk."); - return true; - } - if (context.AllocateChunk(15)) - return true; - context.Output.Header.Chunks[15]->Data.Copy(idsChunk->Data); - - // Convert import options - if (Upgrade_1_To_4_ImportOptions(context)) - return true; - - // Copy atlas image (older version has only single mip) - { - auto srcChunk = context.Input.Header.Chunks[2]; - if (srcChunk == nullptr || srcChunk->IsMissing()) - { - LOG(Warning, "Missing data chunk with a mipmap"); - return true; - } - if (context.AllocateChunk(0)) - return true; - auto dstChunk = context.Output.Header.Chunks[0]; - - dstChunk->Data.Copy(srcChunk->Data); - } - - return false; - } - - static bool Upgrade_1_To_4(AssetMigrationContext& context) - { - ASSERT(context.Input.SerializedVersion == 1 && context.Output.SerializedVersion == 4); - - // Peek asset type - TextureOwnerType1 type; - if (GetOwnerType(context, type)) - return true; - - switch (type) - { - case TextureOwnerType1::Texture: - return Upgrade_1_To_4_Texture(context); - case TextureOwnerType1::CubeTexture: - return Upgrade_1_To_4_CubeTexture(context); - case TextureOwnerType1::SpriteAtlas: - return Upgrade_1_To_4_SpriteAtlas(context); - case TextureOwnerType1::IESProfile: - return Upgrade_1_To_4_IESProfile(context); - case TextureOwnerType1::PreviewsCache: - return Upgrade_1_To_4_PreviewsCache(context); - } - - return true; - } }; #endif diff --git a/Source/Engine/Graphics/Models/ModelData.cpp b/Source/Engine/Graphics/Models/ModelData.cpp index b42288f7f..ff80fadfd 100644 --- a/Source/Engine/Graphics/Models/ModelData.cpp +++ b/Source/Engine/Graphics/Models/ModelData.cpp @@ -97,55 +97,6 @@ void MeshData::InitFromModelVertices(ModelVertex19* vertices, uint32 verticesCou } } -void MeshData::InitFromModelVertices(ModelVertex18* vertices, uint32 verticesCount) -{ - Positions.Resize(verticesCount, false); - UVs.Resize(verticesCount, false); - Normals.Resize(verticesCount, false); - Tangents.Resize(verticesCount, false); - BitangentSigns.Resize(0); - LightmapUVs.Resize(verticesCount, false); - Colors.Resize(0); - BlendIndices.Resize(0); - BlendWeights.Resize(0); - BlendShapes.Resize(0); - - for (uint32 i = 0; i < verticesCount; i++) - { - Positions[i] = vertices->Position; - UVs[i] = vertices->TexCoord.ToFloat2(); - Normals[i] = vertices->Normal.ToFloat3() * 2.0f - 1.0f; - Tangents[i] = vertices->Tangent.ToFloat3() * 2.0f - 1.0f; - LightmapUVs[i] = vertices->LightmapUVs.ToFloat2(); - - vertices++; - } -} - -void MeshData::InitFromModelVertices(ModelVertex15* vertices, uint32 verticesCount) -{ - Positions.Resize(verticesCount, false); - UVs.Resize(verticesCount, false); - Normals.Resize(verticesCount, false); - Tangents.Resize(verticesCount, false); - BitangentSigns.Resize(0); - LightmapUVs.Resize(0); - Colors.Resize(0); - BlendIndices.Resize(0); - BlendWeights.Resize(0); - BlendShapes.Resize(0); - - for (uint32 i = 0; i < verticesCount; i++) - { - Positions[i] = vertices->Position; - UVs[i] = vertices->TexCoord.ToFloat2(); - Normals[i] = vertices->Normal.ToFloat3() * 2.0f - 1.0f; - Tangents[i] = vertices->Tangent.ToFloat3() * 2.0f - 1.0f; - - vertices++; - } -} - void MeshData::InitFromModelVertices(VB0ElementType18* vb0, VB1ElementType18* vb1, uint32 verticesCount) { Positions.Resize(verticesCount, false); @@ -210,31 +161,6 @@ void MeshData::InitFromModelVertices(VB0ElementType18* vb0, VB1ElementType18* vb } } -void MeshData::InitFromModelVertices(VB0ElementType15* vb0, VB1ElementType15* vb1, uint32 verticesCount) -{ - Positions.Resize(verticesCount, false); - UVs.Resize(verticesCount, false); - Normals.Resize(verticesCount, false); - Tangents.Resize(verticesCount, false); - BitangentSigns.Resize(0); - LightmapUVs.Resize(0, false); - Colors.Resize(0); - BlendIndices.Resize(0); - BlendWeights.Resize(0); - BlendShapes.Resize(0); - - for (uint32 i = 0; i < verticesCount; i++) - { - Positions[i] = vb0->Position; - UVs[i] = vb1->TexCoord.ToFloat2(); - Normals[i] = vb1->Normal.ToFloat3() * 2.0f - 1.0f; - Tangents[i] = vb1->Tangent.ToFloat3() * 2.0f - 1.0f; - - vb0++; - vb1++; - } -} - void MeshData::SetIndexBuffer(void* data, uint32 indicesCount) { bool use16BitIndexBuffer = indicesCount <= MAX_uint16; @@ -339,19 +265,6 @@ bool MeshData::Pack2Model(WriteStream* stream) const vb1.Tangent = Float1010102(tangent * 0.5f + 0.5f, static_cast(bitangentSign < 0 ? 1 : 0)); vb1.LightmapUVs = Half2(lightmapUV); stream->WriteBytes(&vb1, sizeof(vb1)); - - // Pack TBN matrix into a quaternion - /*Quaternion quaternionTBN; - bool invertedHandednessTBN; - CalculateQuaternionFromTBN(tangent, bitangent, normal, &quaternionTBN, &invertedHandednessTBN); - quaternionTBN.Normalize(); - uint32 packedQuaternionTBN = QuantizeNormalizedQuaternionWithHandedness(quaternionTBN, invertedHandednessTBN); - - Float4 unpackedQuaternionTBN = Float4(quaternionTBN.X, quaternionTBN.Y, quaternionTBN.Z, ((invertedHandednessTBN ? 0.0f : 128.0f) + (127.0f * (quaternionTBN.W * 0.5f + 0.5f))) / 255.0f); - - //lods.WriteUint32(packedQuaternionTBN); - //lods.WriteFloat4(unpackedQuaternionTBN); - */ } // Vertex Buffer 2 diff --git a/Source/Engine/Graphics/Models/ModelData.h b/Source/Engine/Graphics/Models/ModelData.h index 87b0abe63..ace5709bb 100644 --- a/Source/Engine/Graphics/Models/ModelData.h +++ b/Source/Engine/Graphics/Models/ModelData.h @@ -149,22 +149,6 @@ public: /// Amount of vertices void InitFromModelVertices(ModelVertex19* vertices, uint32 verticesCount); - /// - /// Init from model vertices array - /// [Deprecated on 28.04.2023, expires on 01.01.2024] - /// - /// Array of vertices - /// Amount of vertices - void InitFromModelVertices(ModelVertex18* vertices, uint32 verticesCount); - - /// - /// Init from model vertices array - /// [Deprecated on 28.04.2023, expires on 01.01.2024] - /// - /// Array of vertices - /// Amount of vertices - void InitFromModelVertices(ModelVertex15* vertices, uint32 verticesCount); - /// /// Init from model vertices array /// @@ -182,15 +166,6 @@ public: /// Amount of vertices void InitFromModelVertices(VB0ElementType18* vb0, VB1ElementType18* vb1, VB2ElementType18* vb2, uint32 verticesCount); - /// - /// Init from model vertices array - /// [Deprecated on 28.04.2023, expires on 01.01.2024] - /// - /// Array of data for vertex buffer 0 - /// Array of data for vertex buffer 1 - /// Amount of vertices - void InitFromModelVertices(VB0ElementType15* vb0, VB1ElementType15* vb1, uint32 verticesCount); - /// /// Sets the index buffer data. /// diff --git a/Source/Engine/Graphics/Models/Types.h b/Source/Engine/Graphics/Models/Types.h index 1f57cfa2c..20d574029 100644 --- a/Source/Engine/Graphics/Models/Types.h +++ b/Source/Engine/Graphics/Models/Types.h @@ -70,25 +70,6 @@ enum class MeshBufferType }; // Vertex structure for all models (versioned) -// [Deprecated on 28.04.2023, expires on 01.01.2024] -PACK_STRUCT(struct ModelVertex15 - { - Float3 Position; - Half2 TexCoord; - Float1010102 Normal; - Float1010102 Tangent; - }); - -// [Deprecated on 28.04.2023, expires on 01.01.2024] -PACK_STRUCT(struct ModelVertex18 - { - Float3 Position; - Half2 TexCoord; - Float1010102 Normal; - Float1010102 Tangent; - Half2 LightmapUVs; - }); - // [Deprecated in v1.10] PACK_STRUCT(struct ModelVertex19 { @@ -116,19 +97,6 @@ struct RawModelVertex }; // For vertex data we use three buffers: one with positions, one with other attributes, and one with colors -// [Deprecated on 28.04.2023, expires on 01.01.2024] -PACK_STRUCT(struct VB0ElementType15 - { - Float3 Position; - }); -// [Deprecated on 28.04.2023, expires on 01.01.2024] -PACK_STRUCT(struct VB1ElementType15 - { - Half2 TexCoord; - Float1010102 Normal; - Float1010102 Tangent; - }); - // [Deprecated in v1.10] PACK_STRUCT(struct VB0ElementType18 {