[Bf-blender-cvs] [5e9196ed11e] soc-2020-io-performance: Parse UV coordinates and normals.
Ankit Meel
noreply at git.blender.org
Wed Jul 15 00:33:02 CEST 2020
Commit: 5e9196ed11eb483ac2171047c410731681da376a
Author: Ankit Meel
Date: Wed Jul 15 03:12:35 2020 +0530
Branches: soc-2020-io-performance
https://developer.blender.org/rB5e9196ed11eb483ac2171047c410731681da376a
Parse UV coordinates and normals.
Adding UV to the mesh is not done yet.
Using `std:stoi` seems to add some benefits, so UVs will be added
to mesh after parser is complete.
===================================================================
M source/blender/io/wavefront_obj/intern/wavefront_obj_im_file_reader.cc
M source/blender/io/wavefront_obj/intern/wavefront_obj_im_mesh.cc
M source/blender/io/wavefront_obj/intern/wavefront_obj_im_objects.hh
M source/blender/io/wavefront_obj/intern/wavefront_obj_importer.cc
===================================================================
diff --git a/source/blender/io/wavefront_obj/intern/wavefront_obj_im_file_reader.cc b/source/blender/io/wavefront_obj/intern/wavefront_obj_im_file_reader.cc
index c2d9245626d..82a3831844d 100644
--- a/source/blender/io/wavefront_obj/intern/wavefront_obj_im_file_reader.cc
+++ b/source/blender/io/wavefront_obj/intern/wavefront_obj_im_file_reader.cc
@@ -26,11 +26,11 @@
#include "BKE_context.h"
-#include "BLI_vector.hh"
#include "BLI_string_ref.hh"
+#include "BLI_vector.hh"
-#include "wavefront_obj_im_file_reader.hh"
#include "wavefront_obj_ex_file_writer.hh"
+#include "wavefront_obj_im_file_reader.hh"
namespace blender::io::obj {
@@ -39,6 +39,15 @@ OBJImporter::OBJImporter(const OBJImportParams &import_params) : import_params_(
infile_.open(import_params_.filepath);
}
+static void split_by_char(std::string in_string, char delimiter, Vector<std::string> &r_out_list)
+{
+ std::stringstream stream(in_string);
+ std::string word{};
+ while (std::getline(stream, word, delimiter)) {
+ r_out_list.append(word);
+ }
+}
+
void OBJImporter::parse_and_store(Vector<std::unique_ptr<OBJRawObject>> &list_of_objects)
{
std::string line;
@@ -76,24 +85,41 @@ void OBJImporter::parse_and_store(Vector<std::unique_ptr<OBJRawObject>> &list_of
(*curr_ob)->texture_vertices.append(curr_tex_vert);
}
else if (line_key == "f") {
- Vector<OBJFaceCorner> curr_face;
- while (s_line) {
+ OBJFaceElem curr_face;
+ std::string str_corners_line = s_line.str();
+ Vector<std::string> str_corners_split;
+ split_by_char(str_corners_line, ' ', str_corners_split);
+ for (auto str_corner : str_corners_split) {
+ if (str_corner == "f") {
+ /* Hack, since that's how streams change to strings. Ideally the line_key should be a
+ * string and then a stream is made from the rest of the line. */
+ continue;
+ }
OBJFaceCorner corner;
- if (!(s_line >> corner.vert_index)) {
- break;
+ size_t n_slash = std::count(str_corner.begin(), str_corner.end(), '/');
+ if (n_slash == 0) {
+ corner.vert_index = std::stoi(str_corner);
}
- /* Base 1 in OBJ to base 0 in C++. */
- corner.vert_index--;
- /* Adjust for index offset of previous objects. */
- corner.vert_index -= index_offsets[VERTEX_OFF];
+ else if (n_slash == 1) {
+ Vector<std::string> vert_texture;
+ split_by_char(str_corner, '/', vert_texture);
+ corner.vert_index = std::stoi(vert_texture[0]);
+ corner.tex_vert_index = vert_texture[1].empty() ? -1 : std::stoi(vert_texture[1]);
+ }
+ else if (n_slash == 2) {
+ Vector<std::string> vert_normal;
+ split_by_char(str_corner, '/', vert_normal);
+ corner.vert_index = std::stoi(vert_normal[0]);
+ /* Discard normals. They'll be calculated on the basis of smooth shading flag. */
+ }
+ corner.vert_index -= index_offsets[VERTEX_OFF] + 1;
+ corner.tex_vert_index -= index_offsets[UV_VERTEX_OFF] + 1;
- // TODO texture coords handling. It's mostly string manipulation. Normal indices will be
- // ignored and calculated depending on the smooth flag.
- // s_line >> corner.tex_vert_index;
- curr_face.append(corner);
+ curr_face.face_corners.append(corner);
}
+
(*curr_ob)->face_elements.append(curr_face);
- (*curr_ob)->tot_loop += curr_face.size();
+ (*curr_ob)->tot_loop += curr_face.face_corners.size();
}
else if (line_key == "usemtl") {
(*curr_ob)->material_name.append(s_line.str());
diff --git a/source/blender/io/wavefront_obj/intern/wavefront_obj_im_mesh.cc b/source/blender/io/wavefront_obj/intern/wavefront_obj_im_mesh.cc
index 1221fc2d0a4..ecc870ef51a 100644
--- a/source/blender/io/wavefront_obj/intern/wavefront_obj_im_mesh.cc
+++ b/source/blender/io/wavefront_obj/intern/wavefront_obj_im_mesh.cc
@@ -41,14 +41,14 @@ OBJMeshFromRaw::OBJMeshFromRaw(const class OBJRawObject &curr_object)
int curr_loop_idx = 0;
for (int i = 0; i < curr_object.face_elements.size(); ++i) {
- const Vector<OBJFaceCorner> &curr_face = curr_object.face_elements[i];
+ const OBJFaceElem &curr_face = curr_object.face_elements[i];
MPoly &mpoly = mesh_from_bm_->mpoly[i];
- mpoly.totloop = curr_face.size();
+ mpoly.totloop = curr_face.face_corners.size();
mpoly.loopstart = curr_loop_idx;
- for (int j = 0; j < curr_face.size(); ++j) {
+ for (int j = 0; j < mpoly.totloop; ++j) {
MLoop *mloop = &mesh_from_bm_->mloop[curr_loop_idx];
- mloop->v = curr_face[j].vert_index;
+ mloop->v = curr_face.face_corners[j].vert_index;
curr_loop_idx++;
}
}
diff --git a/source/blender/io/wavefront_obj/intern/wavefront_obj_im_objects.hh b/source/blender/io/wavefront_obj/intern/wavefront_obj_im_objects.hh
index 6cd4702909c..d432aca2f51 100644
--- a/source/blender/io/wavefront_obj/intern/wavefront_obj_im_objects.hh
+++ b/source/blender/io/wavefront_obj/intern/wavefront_obj_im_objects.hh
@@ -35,9 +35,16 @@
namespace blender::io::obj {
typedef struct OBJFaceCorner {
int vert_index;
+ /* -1 is to indicate abscense of UV vertices. Only < 0 condition should be checked since
+ * it can be less than -1 too. */
int tex_vert_index = -1;
} OBJFaceCorner;
+typedef struct OBJFaceElem {
+ bool shaded_smooth = false;
+ Vector<OBJFaceCorner> face_corners;
+} OBJFaceElem;
+
class OBJRawObject {
public:
OBJRawObject(StringRef ob_name) : object_name(ob_name.data()){};
@@ -45,10 +52,9 @@ class OBJRawObject {
std::string object_name;
Vector<MVert> vertices;
Vector<MLoopUV> texture_vertices;
- Vector<Vector<OBJFaceCorner>> face_elements;
+ Vector<OBJFaceElem> face_elements;
uint tot_normals = 0;
uint tot_loop = 0;
- bool is_shaded_smooth;
Vector<std::string> material_name;
};
diff --git a/source/blender/io/wavefront_obj/intern/wavefront_obj_importer.cc b/source/blender/io/wavefront_obj/intern/wavefront_obj_importer.cc
index 51d3ef88a57..c563d3bb21f 100644
--- a/source/blender/io/wavefront_obj/intern/wavefront_obj_importer.cc
+++ b/source/blender/io/wavefront_obj/intern/wavefront_obj_importer.cc
@@ -50,9 +50,9 @@ void OBJImporter::print_obj_data(Vector<std::unique_ptr<OBJRawObject>> &list_of_
print_v2("tex vert", curr_tex_vert.uv);
}
printf("\n");
- for (const Vector<OBJFaceCorner> &curr_face : curr_ob->face_elements) {
- for (OBJFaceCorner a : curr_face) {
- printf("%d ", a.vert_index);
+ for (const OBJFaceElem &curr_face : curr_ob->face_elements) {
+ for (OBJFaceCorner a : curr_face.face_corners) {
+ printf("%d %d ", a.vert_index, a.tex_vert_index);
}
printf("\n");
}
More information about the Bf-blender-cvs
mailing list