#include "DDImage/Attribute.h" #include "DDImage/GeometryList.h" #include "DDImage/GeoReader.h" #include "DDImage/Triangle.h" #include "DDImage/Vector3.h" #include #include #include using namespace DD::Image; namespace my3d { class my3dReader : public GeoReader { public: my3dReader(ReadGeo* readNode); virtual void geometry_engine(Scene& scene, GeometryList& out); static GeoReader* Build(ReadGeo* readNode, int fd, const unsigned char* buf, int bufSize); static bool Test(int fd, const unsigned char* buf, int bufSize); static GeoReader::Description description; }; // // my3dReader methods // my3dReader::my3dReader(ReadGeo* readNode) : GeoReader(readNode) { } void my3dReader::geometry_engine(Scene& scene, GeometryList& out) { const unsigned int kMaxLineLen = 4096; // Open the file std::ifstream in(filename()); // Skip over the header. in.ignore(kMaxLineLen, '\n'); int obj = 0; out.add_object(obj); PointList* points = out.writable_points(obj); Attribute* normals = out.writable_attribute(obj, Group_Primitives, kNormalAttrName, NORMAL_ATTRIB); Attribute* texCoords = out.writable_attribute(obj, Group_Points, kUVAttrName, VECTOR4_ATTRIB); Vector3 pos, normal; Vector4 uv(0, 0, 0, 1); float size; int n = 0; while (in.good()) { in >> size >> pos.x >> pos.y >> pos.z >> normal.x >> normal.y >> normal.z >> uv.x >> uv.y; in.ignore(kMaxLineLen, '\n'); // skip any trailing characters. out.add_primitive(obj, new Triangle(n * 3, n * 3 + 1, n * 3 + 2)); Vector3 v1 = normal.cross(Vector3(1, 0, 0)); Vector3 v2 = v1.cross(normal); v1.normalize(); v2.normalize(); points->push_back(pos); points->push_back(pos + (v1 * size)); points->push_back(pos + (v2 * size)); normals->add(1); normals->normal(n) = normal; texCoords->add(3); texCoords->vector4(n * 3) = uv; texCoords->vector4(n * 3 + 1) = uv + Vector4(size, 0, 0, 0); texCoords->vector4(n * 3 + 2) = uv + Vector4(0, size, 0, 0); ++n; } } // // my3dReader static methods // GeoReader* my3dReader::Build(ReadGeo* readNode, int fd, const unsigned char* buf, int bufSize) { return new my3dReader(readNode); } bool my3dReader::Test(int fd, const unsigned char* buf, int bufSize) { const char* kHeader = "{my3d}"; const int kHeaderLen = strlen(kHeader); // Check that the buffer starts with our header. return (bufSize >= kHeaderLen && strncmp(kHeader, (const char*)buf, kHeaderLen) == 0); } // // my3dReader static variables // GeoReader::Description my3dReader::description("my3d\0", my3dReader::Build, my3dReader::Test); } // namespace my3d