mirror of
https://github.com/PixarAnimationStudios/OpenSubdiv
synced 2025-01-15 19:00:09 +00:00
Merge pull request #448 from davidgyu/patcheval
Fixed gathering of patches near non-manifold topo
This commit is contained in:
commit
99f1b57ba5
@ -194,20 +194,18 @@ offsetAndPermuteIndices(Far::Index const indices[], int count,
|
||||
|
||||
if (permutation) {
|
||||
for (int i = 0; i < count; ++i) {
|
||||
Far::Index index = indices[permutation[i]];
|
||||
if (index == Vtr::INDEX_INVALID) {
|
||||
index = knownGoodIndex;
|
||||
if (permutation[i] < 0) {
|
||||
result[i] = offset + knownGoodIndex;
|
||||
} else {
|
||||
result[i] = offset + indices[permutation[i]];
|
||||
}
|
||||
result[i] = offset + index;
|
||||
}
|
||||
} else if (offset) {
|
||||
for (int i = 0; i < count; ++i) {
|
||||
result[i] = offset + indices[i];
|
||||
}
|
||||
} else {
|
||||
for (int i = 0; i < count; ++i) {
|
||||
Far::Index index = indices[i];
|
||||
if (index == Vtr::INDEX_INVALID) {
|
||||
index = knownGoodIndex;
|
||||
}
|
||||
result[i] = offset + index;
|
||||
}
|
||||
std::memcpy(result, indices, count * sizeof(Far::Index));
|
||||
}
|
||||
}
|
||||
|
||||
@ -1341,9 +1339,35 @@ PatchTablesFactory::populateAdaptivePatches(
|
||||
int transitionMask = patchTag._transitionMask;
|
||||
|
||||
if (!patchTag._isSingleCrease) {
|
||||
int const permuteRegular[16] = { 5, 6, 7, 8, 4, 0, 1, 9, 15, 3, 2, 10, 14, 13, 12, 11 };
|
||||
level->gatherQuadRegularPatchPoints(faceIndex, patchVerts, boundaryMask);
|
||||
offsetAndPermuteIndices(patchVerts, 16, levelVertOffset, permuteRegular, iptrs.R);
|
||||
int const * permutation = 0;
|
||||
|
||||
if (patchTag._boundaryCount == 0) {
|
||||
static int const permuteRegular[16] = { 5, 6, 7, 8, 4, 0, 1, 9, 15, 3, 2, 10, 14, 13, 12, 11 };
|
||||
permutation = permuteRegular;
|
||||
level->gatherQuadRegularInteriorPatchPoints(faceIndex, patchVerts, bIndex);
|
||||
} else if (patchTag._boundaryCount == 1) {
|
||||
// Expand boundary patch vertices and rotate to restore correct orientation.
|
||||
static int const permuteBoundary[4][16] = {
|
||||
{ -1, -1, -1, -1, 11, 3, 0, 4, 10, 2, 1, 5, 9, 8, 7, 6 },
|
||||
{ 9, 10, 11, -1, 8, 2, 3, -1, 7, 1, 0, -1, 6, 5, 4, -1 },
|
||||
{ 6, 7, 8, 9, 5, 1, 2, 10, 4, 0, 3, 11, -1, -1, -1, -1 },
|
||||
{ -1, 4, 5, 6, -1, 0, 1, 7, -1, 3, 2, 8, -1, 11, 10, 9 } };
|
||||
permutation = permuteBoundary[bIndex];
|
||||
level->gatherQuadRegularBoundaryPatchPoints(faceIndex, patchVerts, bIndex);
|
||||
} else if (patchTag._boundaryCount == 2) {
|
||||
// Expand corner patch vertices and rotate to restore correct orientation.
|
||||
static int const permuteCorner[4][16] = {
|
||||
{ -1, -1, -1, -1, -1, 0, 1, 4, -1, 3, 2, 5, -1, 8, 7, 6 },
|
||||
{ -1, -1, -1, -1, 8, 3, 0, -1, 7, 2, 1, -1, 6, 5, 4, -1 },
|
||||
{ 6, 7, 8, -1, 5, 2, 3, -1, 4, 1, 0, -1, -1, -1, -1, -1 },
|
||||
{ -1, 4, 5, 6, -1, 1, 2, 7, -1, 0, 3, 8, -1, -1, -1, -1 } };
|
||||
permutation = permuteCorner[bIndex];
|
||||
level->gatherQuadRegularCornerPatchPoints(faceIndex, patchVerts, bIndex);
|
||||
} else {
|
||||
assert(patchTag._boundaryCount >=0 && patchTag._boundaryCount <= 2);
|
||||
}
|
||||
|
||||
offsetAndPermuteIndices(patchVerts, 16, levelVertOffset, permutation, iptrs.R);
|
||||
|
||||
iptrs.R += 16;
|
||||
pptrs.R = computePatchParam(refiner, ptexIndices, i, faceIndex, boundaryMask, transitionMask, pptrs.R);
|
||||
|
@ -672,111 +672,6 @@ Level::gatherQuadLinearPatchPoints(
|
||||
return 4;
|
||||
}
|
||||
|
||||
//
|
||||
// Gathering the 16 vertices of a quad-regular patch:
|
||||
// - the neighborhood of the face is assumed to be quad-regular
|
||||
// except for the boundaries specified by boundaryMask
|
||||
//
|
||||
// Ordering of resulting vertices:
|
||||
// A complete sequence of 16 vertices is returned including values for
|
||||
// non-existent vertices along boundary and corner edges. The locations of
|
||||
// boundary edges are determined by the specified boundaryMask.
|
||||
// For boundary and corner edges, INDEX_INVALID will be returned for
|
||||
// the corresponding undefined patch vertices. The four vertices of the
|
||||
// face begin the patch.
|
||||
//
|
||||
// | | | |
|
||||
// ---5-----4-----15----14---
|
||||
// | | | |
|
||||
// | | | |
|
||||
// ---6-----0-----3-----13---
|
||||
// | |x x| |
|
||||
// | |x x| |
|
||||
// ---7-----1-----2-----12---
|
||||
// | | | |
|
||||
// | | | |
|
||||
// ---8-----9-----10----11---
|
||||
// | | | |
|
||||
//
|
||||
int
|
||||
Level::gatherQuadRegularPatchPoints(
|
||||
Index thisFace, Index patchPoints[], int boundaryMask, int rotation, int fvarChannel) const {
|
||||
|
||||
Level const& level = *this;
|
||||
|
||||
assert((0 <= rotation) && (rotation < 4));
|
||||
static int const rotationSequence[7] = { 0, 1, 2, 3, 0, 1, 2 };
|
||||
int const * rotatedVerts = &rotationSequence[rotation];
|
||||
|
||||
ConstIndexArray thisFaceVerts = level.getFaceVertices(thisFace);
|
||||
|
||||
ConstIndexArray facePoints = (fvarChannel < 0) ? thisFaceVerts :
|
||||
level.getFVarFaceValues(thisFace, fvarChannel);
|
||||
|
||||
patchPoints[0] = facePoints[rotatedVerts[0]];
|
||||
patchPoints[1] = facePoints[rotatedVerts[1]];
|
||||
patchPoints[2] = facePoints[rotatedVerts[2]];
|
||||
patchPoints[3] = facePoints[rotatedVerts[3]];
|
||||
|
||||
int undefinedPoint = INDEX_INVALID;
|
||||
|
||||
//
|
||||
// For each of the four corner vertices, there may be a face diagonally opposite
|
||||
// the given/central face. Each of these faces contains three points of the
|
||||
// entire ring of points around that given/central face.
|
||||
//
|
||||
int pointIndex = 4;
|
||||
for (int i = 0; i < 4; ++i) {
|
||||
Index v = thisFaceVerts[rotatedVerts[i]];
|
||||
|
||||
ConstIndexArray vFaces = level.getVertexFaces(v);
|
||||
ConstLocalIndexArray vInFaces = level.getVertexFaceLocalIndices(v);
|
||||
|
||||
if (vFaces.size() == 1) {
|
||||
// corner
|
||||
patchPoints[pointIndex++] = undefinedPoint;
|
||||
patchPoints[pointIndex++] = undefinedPoint;
|
||||
patchPoints[pointIndex++] = undefinedPoint;
|
||||
} else if (vFaces.size() == 2) {
|
||||
// boundary
|
||||
int thisFaceInVFaces = vFaces.FindIndex(thisFace);
|
||||
int otherFaceInVFaces = 1 - thisFaceInVFaces;
|
||||
|
||||
Index otherFace = vFaces[otherFaceInVFaces];
|
||||
int vInOtherFace = vInFaces[otherFaceInVFaces];
|
||||
|
||||
facePoints = (fvarChannel < 0) ? level.getFaceVertices(otherFace) :
|
||||
level.getFVarFaceValues(otherFace, fvarChannel);
|
||||
|
||||
if (boundaryMask & (1<<i)) {
|
||||
patchPoints[pointIndex++] = facePoints[fastMod4(vInOtherFace + 3)];
|
||||
patchPoints[pointIndex++] = undefinedPoint;
|
||||
patchPoints[pointIndex++] = undefinedPoint;
|
||||
} else {
|
||||
patchPoints[pointIndex++] = undefinedPoint;
|
||||
patchPoints[pointIndex++] = undefinedPoint;
|
||||
patchPoints[pointIndex++] = facePoints[fastMod4(vInOtherFace + 1)];
|
||||
}
|
||||
} else {
|
||||
// interior
|
||||
int thisFaceInVFaces = vFaces.FindIndexIn4Tuple(thisFace);
|
||||
int intFaceInVFaces = fastMod4(thisFaceInVFaces + 2);
|
||||
|
||||
Index intFace = vFaces[intFaceInVFaces];
|
||||
int vInIntFace = vInFaces[intFaceInVFaces];
|
||||
|
||||
facePoints = (fvarChannel < 0) ? level.getFaceVertices(intFace) :
|
||||
level.getFVarFaceValues(intFace, fvarChannel);
|
||||
|
||||
patchPoints[pointIndex++] = facePoints[fastMod4(vInIntFace + 1)];
|
||||
patchPoints[pointIndex++] = facePoints[fastMod4(vInIntFace + 2)];
|
||||
patchPoints[pointIndex++] = facePoints[fastMod4(vInIntFace + 3)];
|
||||
}
|
||||
}
|
||||
assert(pointIndex == 16);
|
||||
return 16;
|
||||
}
|
||||
|
||||
//
|
||||
// Gathering the 16 vertices of a quad-regular interior patch:
|
||||
// - the neighborhood of the face is assumed to be quad-regular
|
||||
|
@ -309,9 +309,6 @@ public:
|
||||
int gatherQuadLinearPatchPoints(Index fIndex, Index patchPoints[], int rotation = 0,
|
||||
int fvarChannel = -1) const;
|
||||
|
||||
int gatherQuadRegularPatchPoints(Index fIndex, Index patchPoints[], int boundaryMask = 0,
|
||||
int rotation = 0,
|
||||
int fvarChannel = -1) const;
|
||||
int gatherQuadRegularInteriorPatchPoints(Index fIndex, Index patchPoints[], int rotation = 0,
|
||||
int fvarChannel = -1) const;
|
||||
int gatherQuadRegularBoundaryPatchPoints(Index fIndex, Index patchPoints[], int boundaryEdgeInFace,
|
||||
|
Loading…
Reference in New Issue
Block a user