Resolve seam UV map size

master
Jeremy HU 2022-11-02 21:02:45 +11:00
parent 4e861d3d2d
commit 6d71e14b19
4 changed files with 63 additions and 33 deletions

View File

@ -115,31 +115,9 @@ void UvMapGenerator::packUvs()
m_mapPacker->addPart(part); m_mapPacker->addPart(part);
} }
m_mapPacker->pack(); m_mapPacker->addSeams(m_object->seamTriangleUvs);
}
void UvMapGenerator::filterSeamUvs() m_mapPacker->pack();
{
/*
dust3dDebug << "m_object->seamTriangleUvs.size():" << m_object->seamTriangleUvs.size();
std::map<std::array<dust3d::PositionKey, 3>, size_t> triangleMap;
for (size_t i = 0; i < m_object->seamTriangleUvs.size(); ++i) {
for (const auto& it : m_object->seamTriangleUvs[i]) {
triangleMap.insert({ it.first, i });
}
// TODO:
}
std::unordered_set<size_t> seams;
size_t uvTriangleCount = 0;
for (const auto& triangle : m_object->triangles) {
auto findResult = triangleMap.find(std::array<dust3d::PositionKey, 3> { m_object->vertices[triangle[0]], m_object->vertices[triangle[1]], m_object->vertices[triangle[2]] });
if (triangleMap.end() != findResult) {
++uvTriangleCount;
seams.insert(findResult->second);
}
}
dust3dDebug << "uvTriangleCount:" << uvTriangleCount << "seams:" << seams.size();
*/
} }
void UvMapGenerator::generateTextureColorImage() void UvMapGenerator::generateTextureColorImage()
@ -214,7 +192,6 @@ void UvMapGenerator::generate()
if (nullptr == m_snapshot) if (nullptr == m_snapshot)
return; return;
filterSeamUvs();
packUvs(); packUvs();
generateTextureColorImage(); generateTextureColorImage();
generateUvCoords(); generateUvCoords();

View File

@ -45,7 +45,6 @@ private:
void packUvs(); void packUvs();
void generateTextureColorImage(); void generateTextureColorImage();
void generateUvCoords(); void generateUvCoords();
void filterSeamUvs();
}; };
#endif #endif

View File

@ -35,11 +35,60 @@ void UvMapPacker::addPart(const Part& part)
m_partTriangleUvs.push_back(part); m_partTriangleUvs.push_back(part);
} }
void UvMapPacker::addSeams(const std::vector<std::map<std::array<PositionKey, 3>, std::array<Vector2, 3>>>& seamTriangleUvs)
{
for (const auto& it : seamTriangleUvs)
m_seams.push_back(it);
}
void UvMapPacker::resolveSeamUvs()
{
struct TriangleUv {
size_t partIndex;
std::array<Vector2, 3> uv;
};
std::map<std::array<PositionKey, 2>, TriangleUv> halfEdgeToUvMap;
for (size_t partIndex = 0; partIndex < m_partTriangleUvs.size(); ++partIndex) {
const auto& part = m_partTriangleUvs[partIndex];
for (const auto& it : part.localUv) {
halfEdgeToUvMap.insert(std::make_pair(std::array<PositionKey, 2> {
it.first[1], it.first[0] },
TriangleUv { partIndex, it.second }));
halfEdgeToUvMap.insert(std::make_pair(std::array<PositionKey, 2> {
it.first[2], it.first[1] },
TriangleUv { partIndex, it.second }));
halfEdgeToUvMap.insert(std::make_pair(std::array<PositionKey, 2> {
it.first[0], it.first[2] },
TriangleUv { partIndex, it.second }));
}
}
for (size_t seamIndex = 0; seamIndex < m_seams.size(); ++seamIndex) {
const auto& seam = m_seams[seamIndex];
double seamUvMapWidth = 0.0;
double seamUvMapHeight = 0.0;
for (const auto& triangle : seam) {
auto findUv = halfEdgeToUvMap.find({ triangle.first[0], triangle.first[1] });
if (findUv == halfEdgeToUvMap.end())
continue;
const auto& triangleUv = findUv->second;
const auto& part = m_partTriangleUvs[triangleUv.partIndex];
seamUvMapWidth += std::abs(triangleUv.uv[0].x() - triangleUv.uv[1].x()) * part.width;
seamUvMapHeight += std::abs(triangleUv.uv[0].y() - triangleUv.uv[1].y()) * part.height;
}
// dust3dDebug << "Seam uv map size:" << seamUvMapWidth << seamUvMapHeight;
}
// TODO:
}
void UvMapPacker::pack() void UvMapPacker::pack()
{ {
if (m_partTriangleUvs.empty()) if (m_partTriangleUvs.empty())
return; return;
resolveSeamUvs();
std::vector<std::pair<float, float>> chartSizes(m_partTriangleUvs.size()); std::vector<std::pair<float, float>> chartSizes(m_partTriangleUvs.size());
for (size_t i = 0; i < m_partTriangleUvs.size(); ++i) { for (size_t i = 0; i < m_partTriangleUvs.size(); ++i) {
const auto& part = m_partTriangleUvs[i]; const auto& part = m_partTriangleUvs[i];

View File

@ -36,23 +36,25 @@ class UvMapPacker {
public: public:
struct Part { struct Part {
Uuid id; Uuid id;
double width; double width = 0.0;
double height; double height = 0.0;
std::map<std::array<PositionKey, 3>, std::array<Vector2, 3>> localUv; std::map<std::array<PositionKey, 3>, std::array<Vector2, 3>> localUv;
}; };
struct Layout { struct Layout {
Uuid id; Uuid id;
double left; double left = 0.0;
double top; double top = 0.0;
double width; double width = 0.0;
double height; double height = 0.0;
bool flipped; bool flipped = false;
bool isSeam = false;
std::map<std::array<PositionKey, 3>, std::array<Vector2, 3>> globalUv; std::map<std::array<PositionKey, 3>, std::array<Vector2, 3>> globalUv;
}; };
UvMapPacker(); UvMapPacker();
void addPart(const Part& part); void addPart(const Part& part);
void addSeams(const std::vector<std::map<std::array<PositionKey, 3>, std::array<Vector2, 3>>>& seamTriangleUvs);
void pack(); void pack();
const std::vector<Layout>& packedLayouts(); const std::vector<Layout>& packedLayouts();
double packedTextureSize(); double packedTextureSize();
@ -60,7 +62,10 @@ public:
private: private:
std::vector<Part> m_partTriangleUvs; std::vector<Part> m_partTriangleUvs;
std::vector<Layout> m_packedLayouts; std::vector<Layout> m_packedLayouts;
std::vector<std::map<std::array<PositionKey, 3>, std::array<Vector2, 3>>> m_seams;
double m_packedTextureSize = 0.0; double m_packedTextureSize = 0.0;
void resolveSeamUvs();
}; };
} }