Skip to content

Commit 5c11827

Browse files
committed
Support TRIANGLE_FAN and TRIANGLE_STRIP
1 parent 5d461c9 commit 5c11827

File tree

2 files changed

+481
-9
lines changed

2 files changed

+481
-9
lines changed

CesiumRasterOverlays/src/RasterOverlayUtilities.cpp

+41-9
Original file line numberDiff line numberDiff line change
@@ -409,19 +409,24 @@ void copyMetadataTables(const Model& parentModel, Model& result);
409409
* the indices from an index accessor view, or generates new indices.
410410
*/
411411
template <typename TIndex> struct IndicesViewOrGenerator {
412-
IndicesViewOrGenerator(AccessorView<TIndex>&& accessorView_)
413-
: accessorView(accessorView_), indicesCount(accessorView->size()) {}
414-
415-
IndicesViewOrGenerator(int64_t indicesCount_) : indicesCount(indicesCount_) {}
416-
417412
IndicesViewOrGenerator(
418413
const Model& model,
414+
const MeshPrimitive& primitive,
419415
int32_t primitiveIndices,
420-
int64_t numVertices) {
416+
int64_t numVertices)
417+
: primitiveMode(primitive.mode) {
421418
AccessorView<TIndex> view(model, primitiveIndices);
422419
if (view.status() == AccessorViewStatus::Valid) {
423420
accessorView = std::move(view);
424-
indicesCount = accessorView->size();
421+
if (primitiveMode == MeshPrimitive::Mode::TRIANGLES) {
422+
indicesCount = accessorView->size();
423+
} else if (
424+
primitiveMode == MeshPrimitive::Mode::TRIANGLE_STRIP ||
425+
primitiveMode == MeshPrimitive::Mode::TRIANGLE_FAN) {
426+
// With a triangle strip or fan, each additional vertex past the first
427+
// three adds an additional triangle
428+
indicesCount = (accessorView->size() - 2) * 3;
429+
}
425430
} else {
426431
indicesCount = numVertices;
427432
}
@@ -442,8 +447,31 @@ template <typename TIndex> struct IndicesViewOrGenerator {
442447
throw std::range_error("index out of range");
443448
}
444449

445-
if (accessorView) {
450+
if (accessorView && primitiveMode == MeshPrimitive::Mode::TRIANGLES) {
446451
return (*accessorView)[i];
452+
} else if (
453+
accessorView && primitiveMode == MeshPrimitive::Mode::TRIANGLE_STRIP) {
454+
// Indices 0, 1, 2 map normally, indices 3, 4, 5 map to 2, 1, 3,
455+
// indices 6, 7, 8 map to 2, 3, 4, etc.
456+
const int64_t startIndex = i / 3;
457+
const int64_t triIndex = i % 3;
458+
// For every other triangle we need to reverse the order of the first two
459+
// indices to maintain proper winding.
460+
if (startIndex % 2 == 1 && triIndex < 2) {
461+
return triIndex == 0 ? (*accessorView)[startIndex + 1]
462+
: (*accessorView)[startIndex];
463+
}
464+
return (*accessorView)[startIndex + triIndex];
465+
} else if (
466+
accessorView && primitiveMode == MeshPrimitive::Mode::TRIANGLE_FAN) {
467+
// Indices 0, 1, 2 map normally, indices 3, 4, 5 map to 0, 2, 3,
468+
// indices 6, 7, 8 map to 0, 3, 4, etc.
469+
const int64_t startIndex = i / 3;
470+
const int64_t triIndex = i % 3;
471+
if (triIndex == 0) {
472+
return (*accessorView)[0];
473+
}
474+
return (*accessorView)[startIndex + triIndex];
447475
}
448476

449477
// The indices of a non-indexed primitive are simply 0, 1, 2, 3, 4...
@@ -453,6 +481,7 @@ template <typename TIndex> struct IndicesViewOrGenerator {
453481
private:
454482
std::optional<AccessorView<TIndex>> accessorView;
455483
int64_t indicesCount;
484+
int32_t primitiveMode;
456485
};
457486

458487
} // namespace
@@ -958,6 +987,7 @@ bool upsamplePrimitiveForRasterOverlays(
958987
const AccessorView<glm::vec2> uvView(parentModel, uvAccessorIndex);
959988
const IndicesViewOrGenerator<TIndex> indicesView(
960989
parentModel,
990+
primitive,
961991
primitive.indices,
962992
positionAttributeCount);
963993

@@ -1624,7 +1654,9 @@ bool upsamplePrimitiveForRasterOverlays(
16241654
const std::string_view& textureCoordinateAttributeBaseName,
16251655
int32_t textureCoordinateIndex,
16261656
const CesiumGeospatial::Ellipsoid& ellipsoid) {
1627-
if (primitive.mode != MeshPrimitive::Mode::TRIANGLES) {
1657+
if (primitive.mode != MeshPrimitive::Mode::TRIANGLES &&
1658+
primitive.mode != MeshPrimitive::Mode::TRIANGLE_FAN &&
1659+
primitive.mode != MeshPrimitive::Mode::TRIANGLE_STRIP) {
16281660
// Not triangles, so we don't know how to divide this primitive
16291661
// (yet). So remove it.
16301662
return false;

0 commit comments

Comments
 (0)