1/*
2 * Copyright (c) 2024 Huawei Device Co., Ltd.
3 * Licensed under the Apache License, Version 2.0 (the "License");
4 * you may not use this file except in compliance with the License.
5 * You may obtain a copy of the License at
6 *
7 *     http://www.apache.org/licenses/LICENSE-2.0
8 *
9 * Unless required by applicable law or agreed to in writing, software
10 * distributed under the License is distributed on an "AS IS" BASIS,
11 * WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied.
12 * See the License for the specific language governing permissions and
13 * limitations under the License.
14 */
15
16#include "asset_migration.h"
17
18#include <3d/ecs/components/animation_output_component.h>
19#include <core/property/property_types.h>
20
21using namespace BASE_NS;
22using namespace CORE_NS;
23using namespace CORE3D_NS;
24
25SCENE_BEGIN_NAMESPACE()
26
27namespace {
28struct Conversion {
29    PropertyTypeDecl oldVersion;
30    PropertyTypeDecl newVersion;
31};
32
33// Add all datatype conversions here.
34constexpr Conversion conversions[] = {
35
36    { PROPERTYTYPE(Math::IVec2), PropertyType::IVEC2_T }, // Math::IVec2 to BASE_NS::Math::IVec2
37    { PROPERTYTYPE(Math::IVec3), PropertyType::IVEC3_T }, // Math::IVec3 to BASE_NS::Math::IVec3
38    { PROPERTYTYPE(Math::IVec4), PropertyType::IVEC4_T }, // Math::IVec4 to BASE_NS::Math::IVec4
39
40    { PROPERTYTYPE(Math::UVec2), PropertyType::UVEC2_T }, // Math::UVec2 to BASE_NS::Math::UVec2
41    { PROPERTYTYPE(Math::UVec3), PropertyType::UVEC3_T }, // Math::UVec3 to BASE_NS::Math::UVec3
42    { PROPERTYTYPE(Math::UVec4), PropertyType::UVEC4_T }, // Math::UVec4 to BASE_NS::Math::UVec4
43
44    { PROPERTYTYPE(Math::Vec2), PropertyType::VEC2_T }, // Math::Vec2 to BASE_NS::Math::Vec2
45    { PROPERTYTYPE(Math::Vec3), PropertyType::VEC3_T }, // Math::Vec3 to BASE_NS::Math::Vec3
46    { PROPERTYTYPE(Math::Vec4), PropertyType::VEC4_T }, // Math::Vec4 to BASE_NS::Math::Vec4
47
48    { PROPERTYTYPE(Math::Quat), PropertyType::QUAT_T },     // Math::Quat to BASE_NS::Math::Quat
49    { PROPERTYTYPE(Math::Mat3X3), PropertyType::MAT3X3_T }, // Math::Mat3X3 to BASE_NS::Math::Mat3X3
50    { PROPERTYTYPE(Math::Mat4X4), PropertyType::MAT4X4_T }, // Math::Mat4X4 to BASE_NS::Math::Mat4X4
51
52    { PROPERTYTYPE(Uid), PropertyType::UID_T },       // Uid to BASE_NS::Uid
53    { PROPERTYTYPE(string), PropertyType::STRING_T }, // string to BASE_NS::string
54
55    // Array types.
56    { PROPERTYTYPE_ARRAY(Math::IVec2), PropertyType::IVEC2_ARRAY_T }, // Math::IVec2 to BASE_NS::Math::IVec2
57    { PROPERTYTYPE_ARRAY(Math::IVec3), PropertyType::IVEC3_ARRAY_T }, // Math::IVec3 to BASE_NS::Math::IVec3
58    { PROPERTYTYPE_ARRAY(Math::IVec4), PropertyType::IVEC4_ARRAY_T }, // Math::IVec4 to BASE_NS::Math::IVec4
59
60    { PROPERTYTYPE_ARRAY(Math::UVec2), PropertyType::UVEC2_ARRAY_T }, // Math::UVec2 to BASE_NS::Math::UVec2
61    { PROPERTYTYPE_ARRAY(Math::UVec3), PropertyType::UVEC3_ARRAY_T }, // Math::UVec3 to BASE_NS::Math::UVec3
62    { PROPERTYTYPE_ARRAY(Math::UVec4), PropertyType::UVEC4_ARRAY_T }, // Math::UVec4 to BASE_NS::Math::UVec4
63
64    { PROPERTYTYPE_ARRAY(Math::Vec2), PropertyType::VEC2_ARRAY_T }, // Math::Vec2 to BASE_NS::Math::Vec2
65    { PROPERTYTYPE_ARRAY(Math::Vec3), PropertyType::VEC3_ARRAY_T }, // Math::Vec3 to BASE_NS::Math::Vec3
66    { PROPERTYTYPE_ARRAY(Math::Vec4), PropertyType::VEC4_ARRAY_T }, // Math::Vec4 to BASE_NS::Math::Vec4
67
68    { PROPERTYTYPE_ARRAY(Math::Quat), PropertyType::QUAT_ARRAY_T },     // Math::Quat to BASE_NS::Math::Quat
69    { PROPERTYTYPE_ARRAY(Math::Mat3X3), PropertyType::MAT3X3_ARRAY_T }, // Math::Mat3X3 to BASE_NS::Math::Mat3X3
70    { PROPERTYTYPE_ARRAY(Math::Mat4X4), PropertyType::MAT4X4_ARRAY_T }, // Math::Mat4X4 to BASE_NS::Math::Mat4X4
71
72    { PROPERTYTYPE_ARRAY(Uid), PropertyType::UID_ARRAY_T }, // Uid to BASE_NS::Uid
73
74    { PROPERTYTYPE(vector<float>), PropertyType::FLOAT_VECTOR_T },
75    { PROPERTYTYPE(vector<Math::Mat4X4>), PropertyType::MAT4X4_VECTOR_T },
76    { PROPERTYTYPE(vector<EntityReference>), PropertyType::ENTITY_REFERENCE_VECTOR_T }
77
78};
79
80size_t NUMBER_OF_CONVERSIONS = sizeof(conversions) / sizeof(conversions[0]);
81} // namespace
82
83void MigrateAnimation(IEntityCollection& collection)
84{
85    auto* aocm = GetManager<IAnimationOutputComponentManager>(collection.GetEcs());
86    if (aocm) {
87        vector<EntityReference> entities;
88        collection.GetEntitiesRecursive(false, entities);
89        for (const auto& entity : entities) {
90            if (aocm->HasComponent(entity)) {
91                if (auto handle = aocm->Write(entity); handle) {
92                    for (auto i = 0; i < NUMBER_OF_CONVERSIONS; ++i) {
93                        if (handle->type == conversions[i].oldVersion.typeHash) {
94                            handle->type = conversions[i].newVersion.typeHash;
95                            break;
96                        }
97                    }
98                }
99            }
100        }
101    }
102}
103
104SCENE_END_NAMESPACE()
105