14 #include <unordered_map>
21 namespace ply_lineset_reader {
23 struct PLYReaderState {
34 int ReadVertexCallback(p_ply_argument argument) {
35 PLYReaderState *state_ptr;
37 ply_get_argument_user_data(argument,
reinterpret_cast<void **
>(&state_ptr),
39 if (state_ptr->vertex_index >= state_ptr->vertex_num) {
43 double value = ply_get_argument_value(argument);
44 state_ptr->lineset_ptr->points_[state_ptr->vertex_index](index) = value;
46 state_ptr->vertex_index++;
47 ++(*state_ptr->progress_bar);
52 int ReadLineCallback(p_ply_argument argument) {
53 PLYReaderState *state_ptr;
55 ply_get_argument_user_data(argument,
reinterpret_cast<void **
>(&state_ptr),
57 if (state_ptr->line_index >= state_ptr->line_num) {
61 double value = ply_get_argument_value(argument);
62 state_ptr->lineset_ptr->lines_[state_ptr->line_index](index) =
int(value);
64 state_ptr->line_index++;
65 ++(*state_ptr->progress_bar);
70 int ReadColorCallback(p_ply_argument argument) {
71 PLYReaderState *state_ptr;
73 ply_get_argument_user_data(argument,
reinterpret_cast<void **
>(&state_ptr),
75 if (state_ptr->color_index >= state_ptr->color_num) {
79 double value = ply_get_argument_value(argument);
80 state_ptr->lineset_ptr->colors_[state_ptr->color_index](index) =
83 state_ptr->color_index++;
84 ++(*state_ptr->progress_bar);
91 static const std::unordered_map<
93 std::function<bool(
const std::string &, geometry::LineSet &,
bool)>>
94 file_extension_to_lineset_read_function{
98 static const std::unordered_map<std::string,
99 std::function<bool(
const std::string &,
100 const geometry::LineSet &,
104 file_extension_to_lineset_write_function{
113 const std::string &
format,
114 bool print_progress) {
115 auto lineset = std::make_shared<geometry::LineSet>();
122 const std::string &
format,
123 bool print_progress) {
124 std::string filename_ext;
131 if (filename_ext.empty()) {
133 "Read geometry::LineSet failed: unknown file extension.");
136 auto map_itr = file_extension_to_lineset_read_function.find(filename_ext);
137 if (map_itr == file_extension_to_lineset_read_function.end()) {
139 "Read geometry::LineSet failed: unknown file extension.");
142 bool success = map_itr->second(
filename, lineset, print_progress);
152 bool print_progress) {
153 std::string filename_ext =
155 if (filename_ext.empty()) {
157 "Write geometry::LineSet failed: unknown file extension.");
160 auto map_itr = file_extension_to_lineset_write_function.find(filename_ext);
161 if (map_itr == file_extension_to_lineset_write_function.end()) {
163 "Write geometry::LineSet failed: unknown file extension.");
175 bool print_progress) {
176 using namespace ply_lineset_reader;
184 if (!ply_read_header(ply_file)) {
190 PLYReaderState state;
191 state.lineset_ptr = &lineset;
192 state.vertex_num = ply_set_read_cb(ply_file,
"vertex",
"x",
193 ReadVertexCallback, &state, 0);
194 ply_set_read_cb(ply_file,
"vertex",
"y", ReadVertexCallback, &state, 1);
195 ply_set_read_cb(ply_file,
"vertex",
"z", ReadVertexCallback, &state, 2);
197 state.line_num = ply_set_read_cb(ply_file,
"edge",
"vertex1",
198 ReadLineCallback, &state, 0);
199 ply_set_read_cb(ply_file,
"edge",
"vertex2", ReadLineCallback, &state, 1);
201 state.color_num = ply_set_read_cb(ply_file,
"edge",
"red",
202 ReadColorCallback, &state, 0);
203 ply_set_read_cb(ply_file,
"edge",
"green", ReadColorCallback, &state, 1);
204 ply_set_read_cb(ply_file,
"edge",
"blue", ReadColorCallback, &state, 2);
206 if (state.vertex_num <= 0) {
211 if (state.line_num <= 0) {
217 state.vertex_index = 0;
218 state.line_index = 0;
219 state.color_index = 0;
222 lineset.
points_.resize(state.vertex_num);
223 lineset.
lines_.resize(state.line_num);
224 lineset.
colors_.resize(state.color_num);
227 state.vertex_num + state.line_num + state.color_num,
228 "Reading PLY: ", print_progress);
231 if (!ply_read(ply_file)) {
246 bool print_progress) {
256 p_ply ply_file = ply_create(
filename.c_str(),
264 ply_add_comment(ply_file,
"Created by cloudViewer");
265 ply_add_element(ply_file,
"vertex",
266 static_cast<long>(lineset.
points_.size()));
267 ply_add_property(ply_file,
"x", PLY_DOUBLE, PLY_DOUBLE, PLY_DOUBLE);
268 ply_add_property(ply_file,
"y", PLY_DOUBLE, PLY_DOUBLE, PLY_DOUBLE);
269 ply_add_property(ply_file,
"z", PLY_DOUBLE, PLY_DOUBLE, PLY_DOUBLE);
270 ply_add_element(ply_file,
"edge",
static_cast<long>(lineset.
lines_.size()));
271 ply_add_property(ply_file,
"vertex1", PLY_INT, PLY_INT, PLY_INT);
272 ply_add_property(ply_file,
"vertex2", PLY_INT, PLY_INT, PLY_INT);
274 ply_add_property(ply_file,
"red", PLY_UCHAR, PLY_UCHAR, PLY_UCHAR);
275 ply_add_property(ply_file,
"green", PLY_UCHAR, PLY_UCHAR, PLY_UCHAR);
276 ply_add_property(ply_file,
"blue", PLY_UCHAR, PLY_UCHAR, PLY_UCHAR);
278 if (!ply_write_header(ply_file)) {
285 static_cast<size_t>(lineset.
points_.size() + lineset.
lines_.size()),
286 "Writing PLY: ", print_progress);
288 for (
size_t i = 0; i < lineset.
points_.size(); i++) {
289 const Eigen::Vector3d &point = lineset.
points_[i];
290 ply_write(ply_file, point(0));
291 ply_write(ply_file, point(1));
292 ply_write(ply_file, point(2));
295 bool printed_color_warning =
false;
296 for (
size_t i = 0; i < lineset.
lines_.size(); i++) {
298 ply_write(ply_file, line(0));
299 ply_write(ply_file, line(1));
302 if (!printed_color_warning &&
306 "Write Ply clamped color value to valid range");
307 printed_color_warning =
true;
310 ply_write(ply_file,
rgb(0));
311 ply_write(ply_file,
rgb(1));
312 ply_write(ply_file,
rgb(2));
filament::Texture::InternalFormat format
cloudViewer::utility::ConsoleProgressBar * progress_bar
geometry::LineSet * lineset_ptr
LineSet define a sets of lines in 3D. A typical application is to display the point cloud corresponde...
bool HasColors() const
Returns true if the objects lines contains colors.
virtual bool IsEmpty() const override
std::vector< Eigen::Vector3d > points_
Points coordinates.
std::vector< Eigen::Vector3d > colors_
RGB colors of lines.
bool HasLines() const
Returns true if the object contains lines.
std::vector< Eigen::Vector2i > lines_
Lines denoted by the index of points forming the line.
bool WriteLineSetToPLY(const std::string &filename, const geometry::LineSet &lineset, bool write_ascii=false, bool compressed=false, bool print_progress=false)
bool WriteLineSet(const std::string &filename, const geometry::LineSet &lineset, bool write_ascii=false, bool compressed=false, bool print_progress=false)
std::shared_ptr< geometry::LineSet > CreateLineSetFromFile(const std::string &filename, const std::string &format="auto", bool print_progress=false)
bool ReadLineSet(const std::string &filename, geometry::LineSet &lineset, const std::string &format="auto", bool print_progress=false)
bool ReadLineSetFromPLY(const std::string &filename, geometry::LineSet &lineset, bool print_progress=false)
std::string GetFileExtensionInLowerCase(const std::string &filename)
Eigen::Vector3uint8 ColorToUint8(const Eigen::Vector3d &color)
Generic file read and write utility for python interface.
Eigen::Matrix< Index, 2, 1 > Vector2i