Commit 66819375 authored by Romain Pacanowski's avatar Romain Pacanowski

WIP

parent b38e478b
......@@ -9,10 +9,169 @@
#pragma once
#include "mrf/geometry/mesh.hpp"
#include "tinyply/tinyply.h"
namespace mrf
{namespace io
{
namespace io
template<class VEC3_TYPE>
inline void loadMeshFromPLY(std::string const &ply_filename, std::shared_ptr< mrf::geom::_Mesh<VEC3_TYPE> > & a_mesh, unsigned int current_material_index = 0)
{
std::vector<VEC3_TYPE> vertices;
std::vector<VEC3_TYPE> normals;
std::vector<VEC3_TYPE> uvs;
std::vector<unsigned int> enforced_materials;
std::vector<uint> index_faces;
try
{
std::ifstream ss(ply_filename, std::ios::binary);
if (ss.fail())
throw std::runtime_error("failed to open " + ply_filename);
tinyply::PlyFile file;
file.parse_header(ss);
std::cout << "........................................................................" << std::endl;
for (auto c : file.get_comments())
std::cout << "Comment: " << c << " ";
for (auto e : file.get_elements())
{
std::cout << "element - " << e.name << std::flush;
std::cout << "\t" << e.size << std::flush;
for (auto p : e.properties)
{
std::cout << "\tproperty - " << p.name;
std::cout << "\t" << tinyply::PropertyTable[p.propertyType].str;
}
}
std::cout << "........................................................................";
// Tinyply treats parsed data as untyped byte buffers. See below for examples.
std::shared_ptr<tinyply::PlyData> tiny_vertices, tiny_normals, tiny_faces, tiny_texcoords;
// The header information can be used to programmatically extract properties on elements
// known to exist in the header prior to reading the data. For brevity of this sample, properties
// like vertex position are hard-coded:
try
{
tiny_vertices = file.request_properties_from_element("vertex", {"x", "y", "z"});
}
catch (const std::exception &e)
{
std::cerr << "Caught tinyply exception: " << e.what() << std::endl;
throw std::runtime_error( std::string("Caught tinyply exception. NO VERTICES ") + e.what());
}
try
{
tiny_normals = file.request_properties_from_element("vertex", {"nx", "ny", "nz"});
}
catch (const std::exception &e)
{
// FIX ME ! Allow to construct a mesh even without normals... recompute them
std::cerr << "Caught tinyply exception: " << e.what() << std::endl;
throw std::runtime_error( std::string("Caught tinyply exception NO NORMALS")+e.what() );
}
try
{
tiny_texcoords = file.request_properties_from_element("vertex", {"u", "v"});
}
catch (const std::exception &e)
{
tiny_texcoords = nullptr;
}
// Providing a list size hint (the last argument) is a 2x performance improvement. If you have
// arbitrary ply files, it is best to leave this 0.
try
{
tiny_faces = file.request_properties_from_element("face", {"vertex_indices"}, 3);
}
catch (const std::exception &e)
{
std::cerr << "Caught tinyply exception: " << e.what() << std::endl;
throw std::runtime_error( std::string("Caught tinyply exception. NO INDEXES") + e.what());
}
file.read(ss);
if (tiny_vertices)
std::cout << "\tRead vertices:" << tiny_vertices->count;
if (tiny_normals)
std::cout << "\tRead normals:" << tiny_normals->count;
if (tiny_texcoords)
std::cout << "\tRead texcoords:" << tiny_texcoords->count;
if (tiny_faces)
std::cout << "\tRead faces(triangles):" << tiny_faces->count;
const size_t numVerticesBytes = tiny_vertices->buffer.size_bytes();
vertices.resize(tiny_vertices->count);
std::memcpy(vertices.data(), tiny_vertices->buffer.get(), numVerticesBytes);
const size_t numNormalsBytes = tiny_normals->buffer.size_bytes();
normals.resize(tiny_normals->count);
std::memcpy(normals.data(), tiny_normals->buffer.get(), numNormalsBytes);
if (tiny_texcoords)
{
const size_t numUVsBytes = tiny_texcoords->buffer.size_bytes();
uvs.resize(tiny_texcoords->count);
std::memcpy(uvs.data(), tiny_texcoords->buffer.get(), numUVsBytes);
}
else
{
uvs.resize(normals.size(), mrf::math::Vec3f());
}
if (tiny_faces->t != tinyply::Type::UINT32 && tiny_faces->t != tinyply::Type::INT32)
{
std::cerr << " Unsupported PLY index faces type " << ply_filename << std::endl;
throw std::runtime_error("Unsupported PLY index faces type");
}
index_faces.resize(3 * tiny_faces->count);
if (tiny_faces->t != tinyply::Type::UINT32)
{
uint *temp_faces_buffer = reinterpret_cast<uint *>(tiny_faces->buffer.get());
for (uint i_index_faces = 0; i_index_faces < index_faces.size(); i_index_faces++)
{
index_faces[i_index_faces] = temp_faces_buffer[i_index_faces];
}
}
else if (tiny_faces->t != tinyply::Type::INT32)
{
int *temp_faces_buffer = reinterpret_cast<int *>(tiny_faces->buffer.get());
for (uint i_index_faces = 0; i_index_faces < index_faces.size(); i_index_faces++)
{
index_faces[i_index_faces] = uint(temp_faces_buffer[i_index_faces]);
}
}
//Retrieve the current material
enforced_materials.resize(index_faces.size() / 3);
std::fill(enforced_materials.begin(), enforced_materials.end(), current_material_index);
a_mesh = std::make_shared< mrf::geom::_Mesh<VEC3_TYPE> >(Mesh(vertices, normals, uvs, index_faces, enforced_materials));
}
catch (const std::exception &e)
{
std::cerr << "Caught tinyply exception: " << e.what() << std::endl;
throw std::runtime_error("Caught tinyply exception");
}
}
}
\ No newline at end of file
}//end of io namespace
}//end of mrf namespace
\ No newline at end of file
Markdown is supported
0%
or
You are about to add 0 people to the discussion. Proceed with caution.
Finish editing this message first!
Please register or to comment