@@ -948,6 +948,12 @@ cgltf_data* Pipeline::xatlasToCgltf(const cgltf_data* sourceAsset, const xatlas:
948
948
return nullptr ;
949
949
}
950
950
951
+ // Check if baked UVs already exist, in which case they are replaced rather than added.
952
+ auto skipAttribute = [](const cgltf_attribute& attr) {
953
+ const cgltf_int uvindex = gltfio::AssetPipeline::BAKED_UV_ATTRIB_INDEX;
954
+ return attr.type == cgltf_attribute_type_texcoord && attr.index == uvindex;
955
+ };
956
+
951
957
// Determine the number of attributes that will be required, which is the same as the old number
952
958
// of attributes plus an extra UV set per prim.
953
959
size_t numAttributes = 0 ;
@@ -956,6 +962,12 @@ cgltf_data* Pipeline::xatlasToCgltf(const cgltf_data* sourceAsset, const xatlas:
956
962
const cgltf_mesh& mesh = sourceAsset->meshes [i];
957
963
const cgltf_primitive& sourcePrim = mesh.primitives [0 ];
958
964
numAttributes += sourcePrim.attributes_count + 1 ;
965
+ for (size_t ai = 0 ; ai < sourcePrim.attributes_count ; ++ai) {
966
+ if (skipAttribute (sourcePrim.attributes [ai])) {
967
+ numAttributes--;
968
+ break ;
969
+ }
970
+ }
959
971
}
960
972
961
973
// The number of required accessors will be the same as the number of vertex attributes, plus
@@ -983,8 +995,11 @@ cgltf_data* Pipeline::xatlasToCgltf(const cgltf_data* sourceAsset, const xatlas:
983
995
numIndices += atlasMesh.indexCount ;
984
996
cgltf_size floatsPerVert = 0 ;
985
997
for (size_t ai = 0 ; ai < sourcePrim.attributes_count ; ++ai) {
986
- cgltf_type attribType = sourcePrim.attributes [ai].data ->type ;
987
- floatsPerVert += getNumFloats (attribType);
998
+ const cgltf_attribute& attr = sourcePrim.attributes [ai];
999
+ if (skipAttribute (attr)) {
1000
+ continue ;
1001
+ }
1002
+ floatsPerVert += getNumFloats (attr.data ->type );
988
1003
}
989
1004
floatsPerVert += 2 ;
990
1005
numFloats += atlasMesh.vertexCount * floatsPerVert;
@@ -1034,7 +1049,11 @@ cgltf_data* Pipeline::xatlasToCgltf(const cgltf_data* sourceAsset, const xatlas:
1034
1049
const xatlas::Vertex& atlasVertex = atlasMesh.vertexArray [j];
1035
1050
uint32_t sourceIndex = atlasVertex.xref ;
1036
1051
for (size_t ai = 0 ; ai < sourcePrim.attributes_count ; ++ai) {
1037
- const cgltf_accessor* accessor = sourcePrim.attributes [ai].data ;
1052
+ const cgltf_attribute& attr = sourcePrim.attributes [ai];
1053
+ if (skipAttribute (attr)) {
1054
+ continue ;
1055
+ }
1056
+ const cgltf_accessor* accessor = attr.data ;
1038
1057
cgltf_type attribType = accessor->type ;
1039
1058
cgltf_size elementSize = getNumFloats (attribType);
1040
1059
cgltf_accessor_read_float (accessor, sourceIndex, vertexWritePtr, elementSize);
@@ -1066,8 +1085,11 @@ cgltf_data* Pipeline::xatlasToCgltf(const cgltf_data* sourceAsset, const xatlas:
1066
1085
// Determine the vertex stride.
1067
1086
cgltf_size floatsPerVert = 0 ;
1068
1087
for (size_t ai = 0 ; ai < sourcePrim.attributes_count ; ++ai) {
1069
- cgltf_type attribType = sourcePrim.attributes [ai].data ->type ;
1070
- floatsPerVert += getNumFloats (attribType);
1088
+ const cgltf_attribute& attr = sourcePrim.attributes [ai];
1089
+ if (skipAttribute (attr)) {
1090
+ continue ;
1091
+ }
1092
+ floatsPerVert += getNumFloats (attr.data ->type );
1071
1093
}
1072
1094
floatsPerVert += 2 ;
1073
1095
const cgltf_size stride = floatsPerVert * sizeof (float );
@@ -1106,19 +1128,30 @@ cgltf_data* Pipeline::xatlasToCgltf(const cgltf_data* sourceAsset, const xatlas:
1106
1128
resultMesh = sourceMesh;
1107
1129
resultMesh.primitives = &resultPrim;
1108
1130
resultPrim = sourcePrim;
1131
+
1109
1132
resultPrim.attributes = resultAttribute;
1110
1133
resultPrim.attributes_count = sourcePrim.attributes_count + 1 ;
1111
- resultPrim.indices = resultAccessor + sourcePrim.attributes_count + 1 ;
1134
+ for (size_t ai = 0 ; ai < sourcePrim.attributes_count ; ++ai) {
1135
+ if (skipAttribute (sourcePrim.attributes [ai])) {
1136
+ resultPrim.attributes_count --;
1137
+ break ;
1138
+ }
1139
+ }
1140
+
1141
+ resultPrim.indices = resultAccessor + resultPrim.attributes_count ;
1112
1142
cgltf_buffer_view* vertexBufferView = views + i * 2 + 0 ;
1113
1143
cgltf_buffer_view* indexBufferView = views + i * 2 + 1 ;
1114
1144
cgltf_size offset = 0 ;
1115
1145
for (size_t ai = 0 ; ai < sourcePrim.attributes_count ; ++ai) {
1116
- const cgltf_attribute& sourceAttrib = sourcePrim.attributes [ai];
1117
- const cgltf_accessor* sourceAccessor = sourceAttrib.data ;
1146
+ const cgltf_attribute& attr = sourcePrim.attributes [ai];
1147
+ if (skipAttribute (attr)) {
1148
+ continue ;
1149
+ }
1150
+ const cgltf_accessor* sourceAccessor = attr.data ;
1118
1151
*resultAttribute = {
1119
- .name = sourceAttrib .name ,
1120
- .type = sourceAttrib .type ,
1121
- .index = sourceAttrib .index ,
1152
+ .name = attr .name ,
1153
+ .type = attr .type ,
1154
+ .index = attr .index ,
1122
1155
.data = resultAccessor
1123
1156
};
1124
1157
*resultAccessor = {
0 commit comments