[Bf-blender-cvs] [753edaf] master: Alembic: store a pointer to the object reader in the cache modifiers and constraints.
Kévin Dietrich
noreply at git.blender.org
Sat Oct 29 12:25:13 CEST 2016
Commit: 753edafcb77d9aaf07fe869372319b841dd80681
Author: Kévin Dietrich
Date: Sat Oct 29 12:23:09 2016 +0200
Branches: master
https://developer.blender.org/rB753edafcb77d9aaf07fe869372319b841dd80681
Alembic: store a pointer to the object reader in the cache modifiers and
constraints.
This avoids traversing the archive everytime object data is needed and
gives an overall consistent ~2x speedup here with files containing
between 136 and 500 Alembic objects. Also this somewhat nicely de-
duplicates code between data creation (upon import) and data streaming
(modifiers and constraints).
The only worying part is what happens when a CacheFile is deleted and/or
has its path changed. For now, we traverse the whole scene and for each
object using the CacheFile we free the pointer and NULL-ify it (see
BKE_cachefile_clean), but at some point this should be re-considered and
make use of the dependency graph.
===================================================================
M source/blender/alembic/ABC_alembic.h
M source/blender/alembic/intern/abc_curves.cc
M source/blender/alembic/intern/abc_curves.h
M source/blender/alembic/intern/abc_mesh.cc
M source/blender/alembic/intern/abc_mesh.h
M source/blender/alembic/intern/abc_object.cc
M source/blender/alembic/intern/abc_object.h
M source/blender/alembic/intern/abc_points.cc
M source/blender/alembic/intern/abc_points.h
M source/blender/alembic/intern/abc_util.cc
M source/blender/alembic/intern/abc_util.h
M source/blender/alembic/intern/alembic_capi.cc
M source/blender/blenkernel/BKE_cachefile.h
M source/blender/blenkernel/intern/cachefile.c
M source/blender/blenkernel/intern/constraint.c
M source/blender/makesdna/DNA_cachefile_types.h
M source/blender/makesdna/DNA_constraint_types.h
M source/blender/makesdna/DNA_modifier_types.h
M source/blender/makesrna/intern/rna_cachefile.c
M source/blender/makesrna/intern/rna_constraint.c
M source/blender/makesrna/intern/rna_modifier.c
M source/blender/modifiers/intern/MOD_meshsequencecache.c
===================================================================
diff --git a/source/blender/alembic/ABC_alembic.h b/source/blender/alembic/ABC_alembic.h
index e62713f..e92d5f2 100644
--- a/source/blender/alembic/ABC_alembic.h
+++ b/source/blender/alembic/ABC_alembic.h
@@ -28,6 +28,7 @@ extern "C" {
#endif
struct bContext;
+struct CacheReader;
struct DerivedMesh;
struct ListBase;
struct Object;
@@ -92,21 +93,25 @@ AbcArchiveHandle *ABC_create_handle(const char *filename, struct ListBase *objec
void ABC_free_handle(AbcArchiveHandle *handle);
-void ABC_get_transform(AbcArchiveHandle *handle,
- struct Object *ob,
- const char *object_path,
+void ABC_get_transform(struct CacheReader *reader,
float r_mat[4][4],
float time,
float scale);
-struct DerivedMesh *ABC_read_mesh(AbcArchiveHandle *handle,
+struct DerivedMesh *ABC_read_mesh(struct CacheReader *reader,
struct Object *ob,
struct DerivedMesh *dm,
- const char *object_path,
const float time,
const char **err_str,
int flags);
+void CacheReader_free(struct CacheReader *reader);
+
+struct CacheReader *CacheReader_open_alembic_object(struct AbcArchiveHandle *handle,
+ struct CacheReader *reader,
+ struct Object *object,
+ const char *object_path);
+
#ifdef __cplusplus
}
#endif
diff --git a/source/blender/alembic/intern/abc_curves.cc b/source/blender/alembic/intern/abc_curves.cc
index 2b54741..7e5ea3b 100644
--- a/source/blender/alembic/intern/abc_curves.cc
+++ b/source/blender/alembic/intern/abc_curves.cc
@@ -37,6 +37,7 @@ extern "C" {
#include "BLI_listbase.h"
+#include "BKE_cdderivedmesh.h"
#include "BKE_curve.h"
#include "BKE_object.h"
@@ -353,3 +354,54 @@ void read_curve_sample(Curve *cu, const ICurvesSchema &schema, const float time)
BLI_addtail(BKE_curve_nurbs_get(cu), nu);
}
}
+
+/* NOTE: Alembic only stores data about control points, but the DerivedMesh
+ * passed from the cache modifier contains the displist, which has more data
+ * than the control points, so to avoid corrupting the displist we modify the
+ * object directly and create a new DerivedMesh from that. Also we might need to
+ * create new or delete existing NURBS in the curve.
+ */
+DerivedMesh *AbcCurveReader::read_derivedmesh(DerivedMesh */*dm*/, const float time, int /*read_flag*/)
+{
+ ISampleSelector sample_sel(time);
+ const ICurvesSchema::Sample sample = m_curves_schema.getValue(sample_sel);
+
+ const P3fArraySamplePtr &positions = sample.getPositions();
+ const Int32ArraySamplePtr num_vertices = sample.getCurvesNumVertices();
+
+ int vertex_idx = 0;
+ int curve_idx = 0;
+ Curve *curve = static_cast<Curve *>(m_object->data);
+
+ const int curve_count = BLI_listbase_count(&curve->nurb);
+
+ if (curve_count != num_vertices->size()) {
+ BKE_nurbList_free(&curve->nurb);
+ read_curve_sample(curve, m_curves_schema, time);
+ }
+ else {
+ Nurb *nurbs = static_cast<Nurb *>(curve->nurb.first);
+ for (; nurbs; nurbs = nurbs->next, ++curve_idx) {
+ const int totpoint = (*num_vertices)[curve_idx];
+
+ if (nurbs->bp) {
+ BPoint *point = nurbs->bp;
+
+ for (int i = 0; i < totpoint; ++i, ++point, ++vertex_idx) {
+ const Imath::V3f &pos = (*positions)[vertex_idx];
+ copy_yup_zup(point->vec, pos.getValue());
+ }
+ }
+ else if (nurbs->bezt) {
+ BezTriple *bezier = nurbs->bezt;
+
+ for (int i = 0; i < totpoint; ++i, ++bezier, ++vertex_idx) {
+ const Imath::V3f &pos = (*positions)[vertex_idx];
+ copy_yup_zup(bezier->vec[1], pos.getValue());
+ }
+ }
+ }
+ }
+
+ return CDDM_from_curve(m_object);
+}
diff --git a/source/blender/alembic/intern/abc_curves.h b/source/blender/alembic/intern/abc_curves.h
index ee47f19..979ee8a 100644
--- a/source/blender/alembic/intern/abc_curves.h
+++ b/source/blender/alembic/intern/abc_curves.h
@@ -56,10 +56,11 @@ public:
bool valid() const;
void readObjectData(Main *bmain, float time);
+ DerivedMesh *read_derivedmesh(DerivedMesh *, const float time, int);
};
/* ************************************************************************** */
void read_curve_sample(Curve *cu, const Alembic::AbcGeom::ICurvesSchema &schema, const float time);
-#endif /* __ABC_CURVES_H__ */
\ No newline at end of file
+#endif /* __ABC_CURVES_H__ */
diff --git a/source/blender/alembic/intern/abc_mesh.cc b/source/blender/alembic/intern/abc_mesh.cc
index bb5d5ce..5b282e3 100644
--- a/source/blender/alembic/intern/abc_mesh.cc
+++ b/source/blender/alembic/intern/abc_mesh.cc
@@ -646,75 +646,6 @@ void AbcMeshWriter::getGeoGroups(
/* Some helpers for mesh generation */
namespace utils {
-void mesh_add_verts(Mesh *mesh, size_t len)
-{
- if (len == 0) {
- return;
- }
-
- const int totvert = mesh->totvert + len;
- CustomData vdata;
- CustomData_copy(&mesh->vdata, &vdata, CD_MASK_MESH, CD_DEFAULT, totvert);
- CustomData_copy_data(&mesh->vdata, &vdata, 0, 0, mesh->totvert);
-
- if (!CustomData_has_layer(&vdata, CD_MVERT)) {
- CustomData_add_layer(&vdata, CD_MVERT, CD_CALLOC, NULL, totvert);
- }
-
- CustomData_free(&mesh->vdata, mesh->totvert);
- mesh->vdata = vdata;
- BKE_mesh_update_customdata_pointers(mesh, false);
-
- mesh->totvert = totvert;
-}
-
-static void mesh_add_mloops(Mesh *mesh, size_t len)
-{
- if (len == 0) {
- return;
- }
-
- /* new face count */
- const int totloops = mesh->totloop + len;
-
- CustomData ldata;
- CustomData_copy(&mesh->ldata, &ldata, CD_MASK_MESH, CD_DEFAULT, totloops);
- CustomData_copy_data(&mesh->ldata, &ldata, 0, 0, mesh->totloop);
-
- if (!CustomData_has_layer(&ldata, CD_MLOOP)) {
- CustomData_add_layer(&ldata, CD_MLOOP, CD_CALLOC, NULL, totloops);
- }
-
- CustomData_free(&mesh->ldata, mesh->totloop);
- mesh->ldata = ldata;
- BKE_mesh_update_customdata_pointers(mesh, false);
-
- mesh->totloop = totloops;
-}
-
-static void mesh_add_mpolygons(Mesh *mesh, size_t len)
-{
- if (len == 0) {
- return;
- }
-
- const int totpolys = mesh->totpoly + len;
-
- CustomData pdata;
- CustomData_copy(&mesh->pdata, &pdata, CD_MASK_MESH, CD_DEFAULT, totpolys);
- CustomData_copy_data(&mesh->pdata, &pdata, 0, 0, mesh->totpoly);
-
- if (!CustomData_has_layer(&pdata, CD_MPOLY)) {
- CustomData_add_layer(&pdata, CD_MPOLY, CD_CALLOC, NULL, totpolys);
- }
-
- CustomData_free(&mesh->pdata, mesh->totpoly);
- mesh->pdata = pdata;
- BKE_mesh_update_customdata_pointers(mesh, false);
-
- mesh->totpoly = totpolys;
-}
-
static void build_mat_map(const Main *bmain, std::map<std::string, Material *> &mat_map)
{
Material *material = static_cast<Material *>(bmain->mat.first);
@@ -786,45 +717,6 @@ struct AbcMeshData {
UInt32ArraySamplePtr uvs_indices;
};
-static void *add_customdata_cb(void *user_data, const char *name, int data_type)
-{
- Mesh *mesh = static_cast<Mesh *>(user_data);
- CustomDataType cd_data_type = static_cast<CustomDataType>(data_type);
- void *cd_ptr = NULL;
-
- int index = -1;
- if (cd_data_type == CD_MLOOPUV) {
- index = ED_mesh_uv_texture_add(mesh, name, true);
- cd_ptr = CustomData_get_layer(&mesh->ldata, cd_data_type);
- }
- else if (cd_data_type == CD_MLOOPCOL) {
- index = ED_mesh_color_add(mesh, name, true);
- cd_ptr = CustomData_get_layer(&mesh->ldata, cd_data_type);
- }
-
- if (index == -1) {
- return NULL;
- }
-
- return cd_ptr;
-}
-
-CDStreamConfig create_config(Mesh *mesh)
-{
- CDStreamConfig config;
-
- config.mvert = mesh->mvert;
- config.mpoly = mesh->mpoly;
- config.mloop = mesh->mloop;
- config.totpoly = mesh->totpoly;
- config.totloop = mesh->totloop;
- config.user_data = mesh;
- config.loopdata = &mesh->ldata;
- config.add_customdata_cb = add_customdata_cb;
-
- return config;
-}
-
static void read_mverts_interp(MVert *mverts, const P3fArraySamplePtr &positions, const P3fArraySamplePtr &ceil_positions, const float weight)
{
float tmp[3];
@@ -1002,23 +894,15 @@ void AbcMeshReader::readObjectData(Main *bmain, float time)
m_object->data = mesh;
const ISampleSelector sample_sel(time);
- const IPolyMeshSchema::Sample sample = m_schema.getValue(sample_sel);
-
- const P3fArraySamplePtr &positions = sample.getPositions();
- const Int32ArraySamplePtr &face_indices = sample.getFaceIndices();
- const Int32ArraySamplePtr &face_counts = sample.getFaceCounts();
-
- utils::mesh_add_verts(mesh, positions->size());
- utils::mesh_add_mpolygons(mesh, face_counts->size());
- utils::mesh_add_mloops(mesh, face_indices->size());
- m_mesh_data = create_config(mesh);
+ DerivedMesh *dm = CDDM_from_mesh(mesh);
+ DerivedMesh *ndm = this->read_derivedmesh(dm, time, MOD_MESHSEQ_READ_ALL);
- bool has_smooth_normals = false;
- read_mesh_sample(m_settings, m_schema, sample_sel, m_mesh_data, has_smooth_normals);
+ if (ndm != dm) {
+ dm->release(dm);
+ }
- BKE_mesh_calc_normals(mesh);
- BKE_mesh_calc_edges(mesh, false, false);
+ DM_to_mesh(ndm, mesh, m_object, CD_MASK_MESH, true);
if (m_settings->validate_meshes) {
BKE_mesh_validate(mesh, false, false);
@@ -1031,6 +915,120 @@ void AbcMeshReader::readObjectData(Main *bmain, float time)
}
}
+static bool check_smooth_poly_flag(DerivedMesh *dm)
+{
+ MPoly *mpolys = dm->getPolyArray(dm);
+
+ for (int i = 0, e = dm->getNumPolys(dm); i < e; ++i) {
+ MPoly &poly = mpolys[i];
+
+ if ((poly.flag & ME_SMOOTH) != 0) {
+ return true;
+ }
+ }
+
+ return false;
+}
+
+static void set_smooth_poly_flag(DerivedMesh *dm)
+{
+ MPoly *mpolys = dm->getPolyArray(dm);
+
+ for (int i = 0, e = dm->getNumPolys(dm); i < e; ++i) {
+ MPoly &poly = mpolys[i];
+ poly.flag |= ME_SMOOTH;
+ }
+}
+
+static void *add_customdata_cb(void *user_data, const char *name, int data_type)
+{
+ DerivedMesh *dm = static_cast<DerivedMesh *>(user_data);
+ CustomDataType cd_data_type = static_cast<CustomDataType>(data_type);
+ void *cd_ptr = NULL;
+
+ if (ELEM(cd_data_type, CD_MLOOPUV, CD_MLOOPCOL)) {
+ cd_ptr = CustomData_get_layer_named(dm->getLoopDataLayout(dm), cd_data_type, name);
+
+
@@ Diff output truncated at 10240 characters. @@
More information about the Bf-blender-cvs
mailing list