@@ -355,33 +355,23 @@ namespace SR_UTILS_NS {
355355
356356 if (weights.count == 0 ) {
357357 // fallback — чтобы не улетело в (0,0,0)
358- auto * pIdx = reinterpret_cast <SR_MATH_NS::UVector4*>(buffer.GetVertex (v, VertexAttribute::BlendIndices));
359- auto * pW = reinterpret_cast <SR_MATH_NS::FVector4*>(buffer.GetVertex (v, VertexAttribute::BlendWeights));
358+ auto * pIdx = static_cast <SR_MATH_NS::UVector4*>(buffer.GetVertex (v, VertexAttribute::BlendIndices));
359+ auto * pW = static_cast <SR_MATH_NS::FVector4*>(buffer.GetVertex (v, VertexAttribute::BlendWeights));
360360
361361 (*pIdx)[0 ] = 0 ;
362362 (*pW)[0 ] = 1 .0f ;
363363 return ;
364364 }
365365
366366 // 3. сортировка по убыванию веса
367- std::sort (weights.weights , weights.weights + weights.count , [](const BoneWeight& a, const BoneWeight& b) {
367+ std::stable_sort (weights.weights , weights.weights + weights.count , [](const BoneWeight& a, const BoneWeight& b) {
368368 return a.weight > b.weight ;
369369 });
370370
371- // 4. считаем сумму всех весов
372- float totalSum = 0 .0f ;
373- for (uint8_t i = 0 ; i < weights.count ; ++i) {
374- totalSum += weights.weights [i].weight ;
375- }
376-
377- if (totalSum <= 0 .0f ) {
378- SRHalt (" Vertex has zero total bone weight!" );
379- return ;
380- }
381-
382- // 5. решаем: 4 или 8
383- const uint32_t maxInfluences = weights.count > 4 ? std::min<uint32_t >(8 , weights.count ) : std::min<uint32_t >(4 , weights.count );
371+ // 4. выбрать максимум влияний
372+ const uint32_t maxInfluences = std::min<uint32_t >(8 , weights.count );
384373
374+ // 5. сумма ТОЛЬКО выбранных
385375 float selectedSum = 0 .0f ;
386376 for (uint32_t i = 0 ; i < maxInfluences; ++i)
387377 selectedSum += weights.weights [i].weight ;
@@ -394,18 +384,17 @@ namespace SR_UTILS_NS {
394384 // 6. нормализация выбранных
395385 const float invSum = 1 .0f / selectedSum;
396386
397- // 7. запись
398- auto * pIdx1 = reinterpret_cast <SR_MATH_NS::UVector4*>(buffer.GetVertex (v, VertexAttribute::BlendIndices));
399- auto * pW1 = reinterpret_cast <SR_MATH_NS::FVector4*>(buffer.GetVertex (v, VertexAttribute::BlendWeights));
400-
401387 SR_MATH_NS::UVector4 idx1 = {0 ,0 ,0 ,0 };
402388 SR_MATH_NS::FVector4 w1 = {0 ,0 ,0 ,0 };
403389
404390 SR_MATH_NS::UVector4 idx2 = {0 ,0 ,0 ,0 };
405391 SR_MATH_NS::FVector4 w2 = {0 ,0 ,0 ,0 };
406392
407- for (uint32_t i = 0 ; i < maxInfluences; ++i) {
393+ uint32_t used = std::min<uint32_t >(maxInfluences, 8 );
394+
395+ for (uint32_t i = 0 ; i < used; ++i) {
408396 const float w = weights.weights [i].weight * invSum;
397+
409398 if (i < 4 ) {
410399 idx1[i] = weights.weights [i].boneId ;
411400 w1[i] = w;
@@ -416,16 +405,16 @@ namespace SR_UTILS_NS {
416405 }
417406 }
418407
408+ // 7. запись
409+ auto * pIdx1 = static_cast <SR_MATH_NS::UVector4*>(buffer.GetVertex (v, VertexAttribute::BlendIndices));
410+ auto * pW1 = static_cast <SR_MATH_NS::FVector4*>(buffer.GetVertex (v, VertexAttribute::BlendWeights));
411+ auto * pIdx2 = static_cast <SR_MATH_NS::UVector4*>(buffer.GetVertex (v, VertexAttribute::BlendIndices2));
412+ auto * pW2Ptr= static_cast <SR_MATH_NS::FVector4*>(buffer.GetVertex (v, VertexAttribute::BlendWeights2));
413+
419414 *pIdx1 = idx1;
420415 *pW1 = w1;
421-
422- if (maxInfluences > 4 ) {
423- auto * pIdx2 = reinterpret_cast <SR_MATH_NS::UVector4*>(buffer.GetVertex (v, VertexAttribute::BlendIndices2));
424- auto * pW2Ptr= reinterpret_cast <SR_MATH_NS::FVector4*>(buffer.GetVertex (v, VertexAttribute::BlendWeights2));
425-
426- *pIdx2 = idx2;
427- *pW2Ptr= w2;
428- }
416+ *pIdx2 = idx2;
417+ *pW2Ptr= w2;
429418
430419 // 8. проверка
431420 float finalSum = 0 .0f ;
0 commit comments