[Bf-blender-cvs] [b1f1ee1] alembic_basic_io: Partial port of the Python importer to C++.
Kévin Dietrich
noreply at git.blender.org
Sun Mar 27 23:31:13 CEST 2016
Commit: b1f1ee1570708732003e6d54df49d00d54e10511
Author: Kévin Dietrich
Date: Sun Mar 27 23:26:59 2016 +0200
Branches: alembic_basic_io
https://developer.blender.org/rBb1f1ee1570708732003e6d54df49d00d54e10511
Partial port of the Python importer to C++.
For performance reasons, and cleaner code.
TODOs:
- cameras are not imported.
- better handling of the object names.
- object hierarchies/parenting.
===================================================================
M source/blender/alembic/ABC_alembic.h
M source/blender/alembic/intern/alembic_capi.cc
M source/blender/editors/io/io_alembic.c
===================================================================
diff --git a/source/blender/alembic/ABC_alembic.h b/source/blender/alembic/ABC_alembic.h
index 4af4499..1208384 100644
--- a/source/blender/alembic/ABC_alembic.h
+++ b/source/blender/alembic/ABC_alembic.h
@@ -27,6 +27,7 @@
extern "C" {
#endif
+struct bContext;
struct Camera;
struct Curve;
struct DerivedMesh;
@@ -51,8 +52,9 @@ int ABC_export(struct Scene *sce, const char *filename,
int vislayers, int renderable,
int facesets, int matindices,
int geogroups, bool ogawa,
- bool packuv
- );
+ bool packuv);
+
+void ABC_import(struct bContext *C, const char *filename);
void ABC_get_vertex_cache(const char *filepath, float time, void *key, void *verts, int max_verts, const char *sub_obj, int is_mvert);
struct Mesh *ABC_get_mesh(const char *filepath, float time, void *key, int assign_mats, const char *sub_obj, bool *p_only);
diff --git a/source/blender/alembic/intern/alembic_capi.cc b/source/blender/alembic/intern/alembic_capi.cc
index 53f4988..82fe0dc 100644
--- a/source/blender/alembic/intern/alembic_capi.cc
+++ b/source/blender/alembic/intern/alembic_capi.cc
@@ -49,6 +49,56 @@ extern "C" {
#include "BLI_threads.h"
}
+#include <algorithm>
+
+extern "C" {
+#include "DNA_object_types.h"
+#include "DNA_scene_types.h"
+
+#include "BKE_context.h"
+#include "BKE_object.h"
+#include "BKE_scene.h"
+}
+
+static void split(const std::string &s, const char *delim, std::vector<std::string> &v)
+{
+ /* to avoid modifying original string first duplicate the original string
+ * and return a char pointer then free the memory */
+ char *dup = strdup(s.c_str());
+ char *token = strtok(dup, delim);
+
+ while (token != NULL) {
+ v.push_back(std::string(token));
+ /* the call is treated as a subsequent calls to strtok: the function
+ * continues from where it left in previous invocation */
+ token = strtok(NULL, delim);
+ }
+
+ free(dup);
+}
+
+static Object *find_object(Scene *scene, const std::string &sub_object, Object */*parent*/)
+{
+ Object *ret = NULL;
+
+ std::vector<std::string> parts;
+ split(sub_object, "/", parts);
+
+ for (Base *base = static_cast<Base *>(scene->base.first); base; base = base->next) {
+ Object *ob = base->object;
+
+ if (ob->id.name == sub_object) {
+ ret = ob;
+ }
+ }
+
+ if (parts.size() == 1) {
+ return ret;
+ }
+
+ return find_object(scene, sub_object, ret);
+}
+
using namespace Alembic::AbcGeom;
static const int max_alembic_files = 300;
@@ -87,23 +137,6 @@ struct AbcNuInfo {
typedef std::map<void *, AbcInfo> MeshMap;
-static void split(const std::string &s, const char *delim, std::vector<std::string> &v)
-{
- /* to avoid modifying original string first duplicate the original string
- * and return a char pointer then free the memory */
- char *dup = strdup(s.c_str());
- char *token = strtok(dup, delim);
-
- while (token != NULL) {
- v.push_back(std::string(token));
- /* the call is treated as a subsequent calls to strtok: the function
- * continues from where it left in previous invocation */
- token = strtok(NULL, delim);
- }
-
- free(dup);
-}
-
struct alembicManager {
alembicManager()
{
@@ -129,7 +162,7 @@ struct alembicManager {
BLI_mutex_free(mutex);
}
- IArchive *getArchive(std::string filename)
+ IArchive *getArchive(const std::string &filename)
{
std::tr1::unordered_map<std::string, IArchive*>::iterator it = archives.find(filename);
std::tr1::unordered_map< IArchive*, std::tr1::unordered_map<std::string, IObject> >::iterator it_ob;
@@ -1399,3 +1432,141 @@ int ABC_export(Scene *sce, const char *filename,
return BL_ABC_NO_ERR;
}
+
+enum {
+ OBJECT_TYPE_MESH = 0,
+ OBJECT_TYPE_NURBS = 1,
+ OBJECT_TYPE_CAMERA = 2,
+};
+
+static Object *create_hierarchy(bContext *C, const std::string &/*filename*/, const std::vector<std::string> &parts)
+{
+ Object *parent = NULL;
+ std::string sub_object;
+
+ std::vector<std::string>::const_iterator iter;
+ for (iter = parts.begin(); iter != parts.end(); ++iter) {
+ sub_object = "/" + *iter;
+
+ Object *ob = find_object(CTX_data_scene(C), sub_object, parent);
+
+ if (ob) {
+ parent = ob;
+ }
+
+ if (sub_object == "/") {
+ parent = NULL;
+ continue;
+ }
+
+ Object *empty = BKE_object_add(CTX_data_main(C), CTX_data_scene(C), OB_EMPTY, sub_object.c_str());
+ //empty->abc_file = filename;
+ //empty->abc_subobject = sub_object;
+ empty->parent = parent;
+ }
+
+ return parent;
+}
+
+static void import_object(bContext *C, const std::string &filename, const std::string &obname, int object_type, Object *parent)
+{
+ Object *ob = NULL;
+
+ switch (object_type) {
+ case OBJECT_TYPE_MESH:
+ {
+ bool apply_materials = false;
+ bool p_only = false;
+
+ ABC_mutex_lock();
+ Mesh *mesh = ABC_get_mesh(filename.c_str(), 0.0f, NULL, apply_materials, obname.c_str(), &p_only);
+ ABC_mutex_unlock();
+
+ if (!mesh) {
+ ABC_destroy_key(NULL);
+ return;
+ }
+
+ mesh = BKE_mesh_copy(mesh);
+
+ ob = BKE_object_add(CTX_data_main(C), CTX_data_scene(C), OB_MESH, obname.c_str());
+ ob->data = mesh;
+
+ if (apply_materials) {
+ ABC_apply_materials(ob, NULL);
+ }
+
+ ABC_destroy_key(NULL);
+
+ break;
+ }
+ case OBJECT_TYPE_NURBS:
+ {
+ ABC_mutex_lock();
+ Curve *curve = ABC_get_nurbs(filename.c_str(), 0.0f, obname.c_str());
+ ABC_mutex_unlock();
+
+ if (!curve) {
+ return;
+ }
+
+ curve = BKE_curve_copy(curve);
+
+ ob = BKE_object_add(CTX_data_main(C), CTX_data_scene(C), OB_CURVE, obname.c_str());
+ ob->data = curve;
+
+ break;
+ }
+ case OBJECT_TYPE_CAMERA:
+ {
+ /* TODO */
+ break;
+ }
+ }
+
+ if (ob == NULL) {
+ return;
+ }
+
+ ob->parent = parent;
+}
+
+static void import_objects(bContext *C, const std::string &filename, int object_type)
+{
+ /* get objects strings */
+ IArchive *archive = abc_manager->getArchive(filename);
+
+ if (!archive || !archive->valid()) {
+ return;
+ }
+
+ std::vector<std::string> strings;
+ visitObjectString(archive->getTop(), strings, object_type);
+
+ /* Reverse list to go from top to bottom. */
+ std::reverse(strings.begin(), strings.end());
+
+ /* Remove empty strings. */
+ strings.erase(std::remove(strings.begin(), strings.end(), std::string("")),
+ strings.end());
+
+ std::vector<std::string>::iterator iter;
+ for (iter = strings.begin(); iter != strings.end(); ++iter) {
+ std::vector<std::string> parts;
+ split(*iter, "/", parts);
+
+ /* Remove empty strings. */
+ strings.erase(std::remove(parts.begin(), parts.end(), std::string("")),
+ parts.end());
+
+ Object *parent = create_hierarchy(C, filename, parts);
+ import_object(C, filename, *iter, object_type, parent);
+ }
+}
+
+void ABC_import(bContext *C, const char *filename)
+{
+ import_objects(C, filename, OBJECT_TYPE_MESH);
+ import_objects(C, filename, OBJECT_TYPE_NURBS);
+ import_objects(C, filename, OBJECT_TYPE_CAMERA);
+}
diff --git a/source/blender/editors/io/io_alembic.c b/source/blender/editors/io/io_alembic.c
index e37eacc..93323a9c 100644
--- a/source/blender/editors/io/io_alembic.c
+++ b/source/blender/editors/io/io_alembic.c
@@ -169,18 +169,7 @@ static int wm_alembic_import_exec(bContext *C, wmOperator *op)
char filename[FILE_MAX];
RNA_string_get(op->ptr, "filepath", filename);
-#if 0
- /* get objects strings */
-
- char objects_str;
- ABC_get_objects_names(filename, objects_str);
-
- char nurbs_str;
- ABC_get_nurbs_names(filename, nurbs_str);
-
- char camera_str;
- ABC_get_camera_names(filename, camera_str);
-#endif
+ ABC_import(C, filename);
/* restore cursor */
copy_v3_v3(scene->cursor, cursor_location);
More information about the Bf-blender-cvs
mailing list