Add new base normal option: Average

When this option enabled, the mesh generator will average all the base normals of nodes with radius as a weight.
master
Jeremy Hu 2019-06-25 08:14:04 +09:30
parent c76bc4f77c
commit 83cb6383c1
5 changed files with 34 additions and 2 deletions

View File

@ -155,7 +155,7 @@ void AnimalPoser::resolveChainRotation(const std::vector<QString> &limbBoneNames
QVector3D targetMiddleBoneStartPosition;
{
qDebug() << beginBoneName << "Angle:" << angleBetweenDistanceAndMiddleBones << "Distance:" << targetDistanceBetweenBeginAndEndBones;
//qDebug() << beginBoneName << "Angle:" << angleBetweenDistanceAndMiddleBones << "Distance:" << targetDistanceBetweenBeginAndEndBones;
auto rotation = QQuaternion::fromAxisAndAngle(matchRotatePlaneNormal, angleBetweenDistanceAndMiddleBones);
targetMiddleBoneStartPosition = targetEndBoneStartPosition + rotation.rotatedVector(-matchDirectionBetweenBeginAndEndPones).normalized() * targetMiddleBoneLength;
}

View File

@ -457,6 +457,8 @@ nodemesh::Combiner::Mesh *MeshGenerator::combinePartMesh(const QString &partIdSt
builder->setCutRotation(cutRotation);
if (PartBase::YZ == base) {
builder->enableBaseNormalOnX(false);
} else if (PartBase::Average == base) {
builder->enableBaseNormalAverage(true);
} else if (PartBase::XY == base) {
builder->enableBaseNormalOnZ(false);
} else if (PartBase::ZX == base) {
@ -793,7 +795,7 @@ nodemesh::Combiner::Mesh *MeshGenerator::combineMultipleMeshes(const std::vector
for (const auto &it: multipleMeshes) {
const auto &childCombineMode = it.second;
nodemesh::Combiner::Mesh *subMesh = it.first;
qDebug() << "Combine mode:" << CombineModeToString(childCombineMode);
//qDebug() << "Combine mode:" << CombineModeToString(childCombineMode);
if (nullptr == subMesh) {
qDebug() << "Child mesh is null";
continue;

View File

@ -6,6 +6,7 @@
enum class PartBase
{
XYZ = 0,
Average,
YZ,
XY,
ZX,
@ -18,6 +19,8 @@ PartBase PartBaseFromString(const char *baseString)
QString base = baseString; \
if (base == "XYZ") \
return PartBase::XYZ; \
if (base == "Average") \
return PartBase::Average; \
if (base == "YZ") \
return PartBase::YZ; \
if (base == "XY") \
@ -33,6 +36,8 @@ const char *PartBaseToString(PartBase base)
switch (base) { \
case PartBase::XYZ: \
return "XYZ"; \
case PartBase::Average: \
return "Average"; \
case PartBase::YZ: \
return "YZ"; \
case PartBase::XY: \
@ -50,6 +55,8 @@ QString PartBaseToDispName(PartBase base)
switch (base) { \
case PartBase::XYZ: \
return QObject::tr("Dynamic"); \
case PartBase::Average: \
return QObject::tr("Average"); \
case PartBase::YZ: \
return QObject::tr("Side Plane"); \
case PartBase::XY: \

View File

@ -259,6 +259,22 @@ bool Builder::build()
for (const auto &nodeIndex: m_sortedNodeIndices) {
prepareNode(nodeIndex);
}
if (m_baseNormalAverageEnabled) {
QVector3D sumNormal;
for (const auto &node: m_nodes) {
if (node.hasInitialBaseNormal) {
sumNormal += node.initialBaseNormal * node.radius;
}
}
QVector3D averageNormal = sumNormal.normalized();
if (!averageNormal.isNull()) {
for (auto &node: m_nodes) {
if (node.hasInitialBaseNormal) {
node.initialBaseNormal = revisedBaseNormalAcordingToCutNormal(averageNormal, node.traverseDirection);
}
}
}
}
for (const auto &nodeIndex: m_sortedNodeIndices) {
resolveBaseNormalRecursively(nodeIndex);
}
@ -304,6 +320,11 @@ void Builder::enableBaseNormalOnZ(bool enabled)
m_baseNormalOnZ = enabled;
}
void Builder::enableBaseNormalAverage(bool enabled)
{
m_baseNormalAverageEnabled = enabled;
}
std::pair<QVector3D, bool> Builder::calculateBaseNormal(const std::vector<QVector3D> &inputDirects,
const std::vector<QVector3D> &inputPositions,
const std::vector<float> &weights)

View File

@ -20,6 +20,7 @@ public:
void enableBaseNormalOnX(bool enabled);
void enableBaseNormalOnY(bool enabled);
void enableBaseNormalOnZ(bool enabled);
void enableBaseNormalAverage(bool enabled);
const std::vector<QVector3D> &generatedVertices();
const std::vector<std::vector<size_t>> &generatedFaces();
const std::vector<size_t> &generatedVerticesSourceNodeIndices();
@ -98,6 +99,7 @@ private:
bool m_baseNormalOnX = true;
bool m_baseNormalOnY = true;
bool m_baseNormalOnZ = true;
bool m_baseNormalAverageEnabled = false;
void sortNodeIndices();
void prepareNode(size_t nodeIndex);