Skip to content

Commit f1b310b

Browse files
author
Daniel Wickeroth
committed
ANARI: use intensity values for ply point clouds
1 parent dea5f67 commit f1b310b

1 file changed

Lines changed: 84 additions & 4 deletions

File tree

src/OpenCOVER/plugins/ukoeln/ANARI/readPLY.h

Lines changed: 84 additions & 4 deletions
Original file line numberDiff line numberDiff line change
@@ -3,12 +3,21 @@
33
// std
44
#include <cassert>
55
#include <iostream>
6+
#include <algorithm>
7+
#include <cctype>
68
// anari
79
#include <anari/anari_cpp.hpp>
810
#include <anari/anari_cpp/ext/glm.h>
911
// rply
1012
#include "rply.h"
1113

14+
inline std::string toLower(const std::string& str) {
15+
std::string lower = str;
16+
std::transform(lower.begin(), lower.end(), lower.begin(),
17+
[](unsigned char c){ return std::tolower(c); });
18+
return lower;
19+
}
20+
1221
inline int rplyReadVertexCallback(p_ply_argument arg)
1322
{
1423
long axis;
@@ -41,6 +50,25 @@ inline int rplyReadColorCallback(p_ply_argument arg)
4150
return 1;
4251
}
4352

53+
inline int rplyReadIntensityCallback(p_ply_argument arg)
54+
{
55+
long axis;
56+
void *pointer;
57+
ply_get_argument_user_data(arg, &pointer, &axis);
58+
auto **colors = (glm::vec3 **)pointer;
59+
float val = ply_get_argument_value(arg);
60+
61+
static unsigned long count = 0;
62+
// Normalize intensity to 0-1 range (assuming it's 0-255, adjust if needed)
63+
float normalized = val > 1.0f ? val/255.f : val;
64+
(*colors)[count][0] = normalized;
65+
(*colors)[count][1] = normalized;
66+
(*colors)[count][2] = normalized;
67+
count++;
68+
69+
return 1;
70+
}
71+
4472
anari::Surface readPLY(anari::Device device, std::string fn, float radius)
4573
{
4674
p_ply ply = ply_open(fn.c_str(), NULL, 0, NULL);
@@ -50,14 +78,58 @@ anari::Surface readPLY(anari::Device device, std::string fn, float radius)
5078
}
5179

5280
glm::vec3 *positions = nullptr, *colors = nullptr;
53-
81+
82+
// Detect what color data is available
83+
bool hasVertexColors = false;
84+
std::string intensityPropertyName;
85+
86+
// Check for vertex colors (red, green, blue)
87+
p_ply_element element = nullptr;
88+
while ((element = ply_get_next_element(ply, element))) {
89+
const char *elemName;
90+
long nInstances;
91+
ply_get_element_info(element, &elemName, &nInstances);
92+
93+
if (std::string(elemName) == "vertex") {
94+
p_ply_property property = nullptr;
95+
bool hasRed = false, hasGreen = false, hasBlue = false;
96+
97+
while ((property = ply_get_next_property(element, property))) {
98+
const char *propName;
99+
ply_get_property_info(property, &propName, nullptr, nullptr, nullptr);
100+
std::string propNameStr(propName);
101+
102+
if (propNameStr == "red") hasRed = true;
103+
if (propNameStr == "green") hasGreen = true;
104+
if (propNameStr == "blue") hasBlue = true;
105+
106+
// Check for intensity property (case-insensitive)
107+
if (intensityPropertyName.empty() &&
108+
toLower(propNameStr).find("intensity") != std::string::npos) {
109+
intensityPropertyName = propNameStr;
110+
}
111+
}
112+
113+
hasVertexColors = hasRed && hasGreen && hasBlue;
114+
break;
115+
}
116+
}
117+
54118
long numSpheres = ply_set_read_cb(ply, "vertex", "x", rplyReadVertexCallback, &positions, 0);
55119
ply_set_read_cb(ply, "vertex", "y", rplyReadVertexCallback, &positions, 1);
56120
ply_set_read_cb(ply, "vertex", "z", rplyReadVertexCallback, &positions, 2);
57121

58-
ply_set_read_cb(ply, "vertex", "red", rplyReadColorCallback, &colors, 0);
59-
ply_set_read_cb(ply, "vertex", "green", rplyReadColorCallback, &colors, 1);
60-
ply_set_read_cb(ply, "vertex", "blue", rplyReadColorCallback, &colors, 2);
122+
// Set up color callbacks based on what's available
123+
if (hasVertexColors) {
124+
std::cout << "ANARI::Using vertex colors from PLY file.\n";
125+
ply_set_read_cb(ply, "vertex", "red", rplyReadColorCallback, &colors, 0);
126+
ply_set_read_cb(ply, "vertex", "green", rplyReadColorCallback, &colors, 1);
127+
ply_set_read_cb(ply, "vertex", "blue", rplyReadColorCallback, &colors, 2);
128+
} else if (!intensityPropertyName.empty()) {
129+
std::cout << "ANARI::Using intensity property '" << intensityPropertyName << "' for grayscale colors from PLY file.\n";
130+
ply_set_read_cb(ply, "vertex", intensityPropertyName.c_str(),
131+
rplyReadIntensityCallback, &colors, 0);
132+
}
61133

62134
auto positionsArray =
63135
anari::newArray1D(device, ANARI_FLOAT32_VEC3, numSpheres);
@@ -68,6 +140,14 @@ anari::Surface readPLY(anari::Device device, std::string fn, float radius)
68140
positions = anari::map<glm::vec3>(device, positionsArray);
69141
colors = anari::map<glm::vec3>(device, colorsArray);
70142

143+
// If no color data will be read, initialize with medium gray
144+
if (!hasVertexColors && intensityPropertyName.empty()) {
145+
std::cout << "ANARI::No color information found in PLY file. Using default gray color.\n";
146+
for (long i = 0; i < numSpheres; ++i) {
147+
colors[i] = glm::vec3(0.5f, 0.5f, 0.5f);
148+
}
149+
}
150+
71151
if (!ply_read(ply)) {
72152
std::cerr << "Cound not read file: " << fn << '\n';
73153
return nullptr;

0 commit comments

Comments
 (0)