diff options
author | Lukas Stockner <lukas.stockner@freenet.de> | 2017-05-02 14:19:09 +0300 |
---|---|---|
committer | Lukas Stockner <lukas.stockner@freenet.de> | 2017-05-02 14:43:05 +0300 |
commit | ea109fa4a683da973052b778b440cf9d671cf1b1 (patch) | |
tree | eb24dfe673b2e7ddd512f03456eb6735cf2d7f54 /source | |
parent | 87674f432ec8d6006c2afff018dd42907728afaf (diff) | |
parent | fc8f428224a8e77ba66394ad8238a406fa24ee3a (diff) |
Merge remote-tracking branch 'origin/master' into temp-cycles-denoising
Diffstat (limited to 'source')
40 files changed, 439 insertions, 210 deletions
diff --git a/source/blender/alembic/ABC_alembic.h b/source/blender/alembic/ABC_alembic.h index 6b698e5ec66..6228ae60c56 100644 --- a/source/blender/alembic/ABC_alembic.h +++ b/source/blender/alembic/ABC_alembic.h @@ -121,6 +121,7 @@ struct DerivedMesh *ABC_read_mesh(struct CacheReader *reader, const char **err_str, int flags); +void CacheReader_incref(struct CacheReader *reader); void CacheReader_free(struct CacheReader *reader); struct CacheReader *CacheReader_open_alembic_object(struct AbcArchiveHandle *handle, diff --git a/source/blender/alembic/intern/abc_archive.cc b/source/blender/alembic/intern/abc_archive.cc index 5f8fc1a3739..194a8224c62 100644 --- a/source/blender/alembic/intern/abc_archive.cc +++ b/source/blender/alembic/intern/abc_archive.cc @@ -28,6 +28,8 @@ # include "utfconv.h" #endif +#include <fstream> + using Alembic::Abc::Exception; using Alembic::Abc::ErrorHandler; using Alembic::Abc::IArchive; @@ -38,8 +40,9 @@ static IArchive open_archive(const std::string &filename, const std::vector<std::istream *> &input_streams, bool &is_hdf5) { + is_hdf5 = false; + try { - is_hdf5 = false; Alembic::AbcCoreOgawa::ReadArchive archive_reader(input_streams); return IArchive(archive_reader(filename), @@ -63,6 +66,27 @@ static IArchive open_archive(const std::string &filename, return IArchive(); } #else + /* Inspect the file to see whether it's really a HDF5 file. */ + char header[4]; /* char(0x89) + "HDF" */ + std::ifstream the_file(filename.c_str(), std::ios::in | std::ios::binary); + if (!the_file) { + std::cerr << "Unable to open " << filename << std::endl; + } + else if (!the_file.read(header, sizeof(header))) { + std::cerr << "Unable to read from " << filename << std::endl; + } + else if (strncmp(header + 1, "HDF", 3)) { + std::cerr << filename << " has an unknown file format, unable to read." << std::endl; + } + else { + is_hdf5 = true; + std::cerr << filename << " is in the obsolete HDF5 format, unable to read." << std::endl; + } + + if (the_file.is_open()) { + the_file.close(); + } + return IArchive(); #endif } @@ -83,16 +107,20 @@ ArchiveReader::ArchiveReader(const char *filename) m_streams.push_back(&m_infile); - bool is_hdf5; - m_archive = open_archive(filename, m_streams, is_hdf5); + m_archive = open_archive(filename, m_streams, m_is_hdf5); /* We can't open an HDF5 file from a stream, so close it. */ - if (is_hdf5) { + if (m_is_hdf5) { m_infile.close(); m_streams.clear(); } } +bool ArchiveReader::is_hdf5() const +{ + return m_is_hdf5; +} + bool ArchiveReader::valid() const { return m_archive.valid(); diff --git a/source/blender/alembic/intern/abc_archive.h b/source/blender/alembic/intern/abc_archive.h index d412574b736..84309fbc9df 100644 --- a/source/blender/alembic/intern/abc_archive.h +++ b/source/blender/alembic/intern/abc_archive.h @@ -44,12 +44,21 @@ class ArchiveReader { Alembic::Abc::IArchive m_archive; std::ifstream m_infile; std::vector<std::istream *> m_streams; + bool m_is_hdf5; public: explicit ArchiveReader(const char *filename); bool valid() const; + /** + * Returns true when either Blender is compiled with HDF5 support and + * the archive was succesfully opened (valid() will also return true), + * or when Blender was built without HDF5 support but a HDF5 file was + * detected (valid() will return false). + */ + bool is_hdf5() const; + Alembic::Abc::IObject getTop(); }; diff --git a/source/blender/alembic/intern/abc_camera.cc b/source/blender/alembic/intern/abc_camera.cc index 33344f6c9c5..16416205983 100644 --- a/source/blender/alembic/intern/abc_camera.cc +++ b/source/blender/alembic/intern/abc_camera.cc @@ -117,6 +117,23 @@ bool AbcCameraReader::valid() const return m_schema.valid(); } +bool AbcCameraReader::accepts_object_type(const Alembic::AbcCoreAbstract::ObjectHeader &alembic_header, + const Object *const ob, + const char **err_str) const +{ + if (!Alembic::AbcGeom::ICamera::matches(alembic_header)) { + *err_str = "Object type mismatch, Alembic object path pointed to Camera when importing, but not any more."; + return false; + } + + if (ob->type != OB_CAMERA) { + *err_str = "Object type mismatch, Alembic object path points to Camera."; + return false; + } + + return true; +} + void AbcCameraReader::readObjectData(Main *bmain, const ISampleSelector &sample_sel) { Camera *bcam = static_cast<Camera *>(BKE_camera_add(bmain, m_data_name.c_str())); diff --git a/source/blender/alembic/intern/abc_camera.h b/source/blender/alembic/intern/abc_camera.h index 0201dd9d6e1..16c5cccd5ea 100644 --- a/source/blender/alembic/intern/abc_camera.h +++ b/source/blender/alembic/intern/abc_camera.h @@ -54,6 +54,9 @@ public: AbcCameraReader(const Alembic::Abc::IObject &object, ImportSettings &settings); bool valid() const; + bool accepts_object_type(const Alembic::AbcCoreAbstract::ObjectHeader &alembic_header, + const Object *const ob, + const char **err_str) const; void readObjectData(Main *bmain, const Alembic::Abc::ISampleSelector &sample_sel); }; diff --git a/source/blender/alembic/intern/abc_curves.cc b/source/blender/alembic/intern/abc_curves.cc index d85d8df4d77..67b2cb8ae8c 100644 --- a/source/blender/alembic/intern/abc_curves.cc +++ b/source/blender/alembic/intern/abc_curves.cc @@ -211,6 +211,23 @@ bool AbcCurveReader::valid() const return m_curves_schema.valid(); } +bool AbcCurveReader::accepts_object_type(const Alembic::AbcCoreAbstract::ObjectHeader &alembic_header, + const Object *const ob, + const char **err_str) const +{ + if (!Alembic::AbcGeom::ICurves::matches(alembic_header)) { + *err_str = "Object type mismatch, Alembic object path pointed to Curves when importing, but not any more."; + return false; + } + + if (ob->type != OB_EMPTY) { + *err_str = "Object type mismatch, Alembic object path points to Curves."; + return false; + } + + return true; +} + void AbcCurveReader::readObjectData(Main *bmain, const Alembic::Abc::ISampleSelector &sample_sel) { Curve *cu = BKE_curve_add(bmain, m_data_name.c_str(), OB_CURVE); diff --git a/source/blender/alembic/intern/abc_curves.h b/source/blender/alembic/intern/abc_curves.h index 1ad6d0bf278..a9231f947b2 100644 --- a/source/blender/alembic/intern/abc_curves.h +++ b/source/blender/alembic/intern/abc_curves.h @@ -54,6 +54,9 @@ public: AbcCurveReader(const Alembic::Abc::IObject &object, ImportSettings &settings); bool valid() const; + bool accepts_object_type(const Alembic::AbcCoreAbstract::ObjectHeader &alembic_header, + const Object *const ob, + const char **err_str) const; void readObjectData(Main *bmain, const Alembic::Abc::ISampleSelector &sample_sel); DerivedMesh *read_derivedmesh(DerivedMesh *dm, diff --git a/source/blender/alembic/intern/abc_exporter.cc b/source/blender/alembic/intern/abc_exporter.cc index d70b9625f1d..11c63461ab4 100644 --- a/source/blender/alembic/intern/abc_exporter.cc +++ b/source/blender/alembic/intern/abc_exporter.cc @@ -108,7 +108,7 @@ static bool object_is_smoke_sim(Object *ob) return false; } -static bool object_is_shape(Object *ob) +static bool object_type_is_exportable(Object *ob) { switch (ob->type) { case OB_MESH: @@ -117,6 +117,7 @@ static bool object_is_shape(Object *ob) } return true; + case OB_EMPTY: case OB_CURVE: case OB_SURF: case OB_CAMERA: @@ -387,7 +388,7 @@ void AbcExporter::exploreTransform(EvaluationContext *eval_ctx, Object *ob, Obje return; } - if (object_is_shape(ob)) { + if (object_type_is_exportable(ob)) { createTransformWriter(ob, parent, dupliObParent); } @@ -552,7 +553,7 @@ void AbcExporter::createParticleSystemsWriters(Object *ob, AbcTransformWriter *x void AbcExporter::createShapeWriter(Object *ob, Object *dupliObParent) { - if (!object_is_shape(ob)) { + if (!object_type_is_exportable(ob)) { return; } diff --git a/source/blender/alembic/intern/abc_hair.cc b/source/blender/alembic/intern/abc_hair.cc index 9a974273a46..2d42c532c9b 100644 --- a/source/blender/alembic/intern/abc_hair.cc +++ b/source/blender/alembic/intern/abc_hair.cc @@ -241,7 +241,6 @@ void AbcHairWriter::write_hair_child_sample(DerivedMesh *dm, invert_m4_m4_safe(inv_mat, m_object->obmat); MTFace *mtface = static_cast<MTFace *>(CustomData_get_layer(&dm->faceData, CD_MTFACE)); - MFace *mface = dm->getTessFaceArray(dm); MVert *mverts = dm->getVertArray(dm); ParticleCacheKey **cache = m_psys->childcache; @@ -253,12 +252,25 @@ void AbcHairWriter::write_hair_child_sample(DerivedMesh *dm, path = cache[p]; if (part->from == PART_FROM_FACE) { - const int num = pc->num; + if (part->childtype == PART_CHILD_PARTICLES || !mtface) { + /* Face index is unknown for these particles, so just take info + * from the parent. */ + uv_values.push_back(uv_values[pc->parent]); + norm_values.push_back(norm_values[pc->parent]); + } + else { + const int num = pc->num; + if (num < 0) { + ABC_LOG(m_settings.logger) + << "Warning, child particle of hair system " << m_psys->name + << " has unknown face index of geometry of "<< (m_object->id.name + 2) + << ", skipping child hair." << std::endl; + continue; + } - MFace *face = static_cast<MFace *>(dm->getTessFaceData(dm, num, CD_MFACE)); - MTFace *tface = mtface + num; + MFace *face = static_cast<MFace *>(dm->getTessFaceData(dm, num, CD_MFACE)); + MTFace *tface = mtface + num; - if (mface && mtface) { float r_uv[2], tmpnor[3], mapfw[4], vec[3]; psys_interpolate_uvs(tface, face->v4, pc->fuv, r_uv); @@ -270,6 +282,14 @@ void AbcHairWriter::write_hair_child_sample(DerivedMesh *dm, norm_values.push_back(Imath::V3f(tmpnor[0], tmpnor[2], -tmpnor[1])); } } + else { + ABC_LOG(m_settings.logger) + << "Unknown particle type " << part->from + << " for child hair of system " << m_psys->name + << std::endl; + uv_values.push_back(uv_values[pc->parent]); + norm_values.push_back(norm_values[pc->parent]); + } int steps = path->segments + 1; hvertices.push_back(steps); diff --git a/source/blender/alembic/intern/abc_mesh.cc b/source/blender/alembic/intern/abc_mesh.cc index 39186ec55dc..32795e70e92 100644 --- a/source/blender/alembic/intern/abc_mesh.cc +++ b/source/blender/alembic/intern/abc_mesh.cc @@ -1048,6 +1048,23 @@ void AbcMeshReader::readObjectData(Main *bmain, const Alembic::Abc::ISampleSelec } } +bool AbcMeshReader::accepts_object_type(const Alembic::AbcCoreAbstract::ObjectHeader &alembic_header, + const Object *const ob, + const char **err_str) const +{ + if (!Alembic::AbcGeom::IPolyMesh::matches(alembic_header)) { + *err_str = "Object type mismatch, Alembic object path pointed to PolyMesh when importing, but not any more."; + return false; + } + + if (ob->type != OB_MESH) { + *err_str = "Object type mismatch, Alembic object path points to PolyMesh."; + return false; + } + + return true; +} + DerivedMesh *AbcMeshReader::read_derivedmesh(DerivedMesh *dm, const ISampleSelector &sample_sel, int read_flag, @@ -1239,6 +1256,23 @@ bool AbcSubDReader::valid() const return m_schema.valid(); } +bool AbcSubDReader::accepts_object_type(const Alembic::AbcCoreAbstract::ObjectHeader &alembic_header, + const Object *const ob, + const char **err_str) const +{ + if (!Alembic::AbcGeom::ISubD::matches(alembic_header)) { + *err_str = "Object type mismatch, Alembic object path pointed to SubD when importing, but not any more."; + return false; + } + + if (ob->type != OB_MESH) { + *err_str = "Object type mismatch, Alembic object path points to SubD."; + return false; + } + + return true; +} + void AbcSubDReader::readObjectData(Main *bmain, const Alembic::Abc::ISampleSelector &sample_sel) { Mesh *mesh = BKE_mesh_add(bmain, m_data_name.c_str()); diff --git a/source/blender/alembic/intern/abc_mesh.h b/source/blender/alembic/intern/abc_mesh.h index 1b67c80cc72..6bf1dde3d1d 100644 --- a/source/blender/alembic/intern/abc_mesh.h +++ b/source/blender/alembic/intern/abc_mesh.h @@ -99,7 +99,9 @@ public: AbcMeshReader(const Alembic::Abc::IObject &object, ImportSettings &settings); bool valid() const; - + bool accepts_object_type(const Alembic::AbcCoreAbstract::ObjectHeader &alembic_header, + const Object *const ob, + const char **err_str) const; void readObjectData(Main *bmain, const Alembic::Abc::ISampleSelector &sample_sel); DerivedMesh *read_derivedmesh(DerivedMesh *dm, @@ -123,7 +125,9 @@ public: AbcSubDReader(const Alembic::Abc::IObject &object, ImportSettings &settings); bool valid() const; - + bool accepts_object_type(const Alembic::AbcCoreAbstract::ObjectHeader &alembic_header, + const Object *const ob, + const char **err_str) const; void readObjectData(Main *bmain, const Alembic::Abc::ISampleSelector &sample_sel); DerivedMesh *read_derivedmesh(DerivedMesh *dm, const Alembic::Abc::ISampleSelector &sample_sel, diff --git a/source/blender/alembic/intern/abc_object.cc b/source/blender/alembic/intern/abc_object.cc index 4c3c060be28..04f6da48711 100644 --- a/source/blender/alembic/intern/abc_object.cc +++ b/source/blender/alembic/intern/abc_object.cc @@ -160,15 +160,6 @@ void AbcObjectReader::object(Object *ob) m_object = ob; } -DerivedMesh *AbcObjectReader::read_derivedmesh(DerivedMesh *dm, - const Alembic::Abc::ISampleSelector &UNUSED(sample_sel), - int UNUSED(read_flag), - const char **UNUSED(err_str)) -{ - return dm; -} - - static Imath::M44d blend_matrices(const Imath::M44d &m0, const Imath::M44d &m1, const float weight) { float mat0[4][4], mat1[4][4], ret[4][4]; @@ -224,6 +215,14 @@ Imath::M44d get_matrix(const IXformSchema &schema, const float time) return s0.getMatrix(); } +DerivedMesh *AbcObjectReader::read_derivedmesh(DerivedMesh *dm, + const Alembic::Abc::ISampleSelector &UNUSED(sample_sel), + int UNUSED(read_flag), + const char **UNUSED(err_str)) +{ + return dm; +} + void AbcObjectReader::setupObjectTransform(const float time) { bool is_constant = false; @@ -371,4 +370,5 @@ void AbcObjectReader::incref() void AbcObjectReader::decref() { --m_refcount; + BLI_assert(m_refcount >= 0); } diff --git a/source/blender/alembic/intern/abc_object.h b/source/blender/alembic/intern/abc_object.h index a9dbaa89c97..1462f93a422 100644 --- a/source/blender/alembic/intern/abc_object.h +++ b/source/blender/alembic/intern/abc_object.h @@ -169,13 +169,16 @@ public: const std::string & data_name() const { return m_data_name; } virtual bool valid() const = 0; + virtual bool accepts_object_type(const Alembic::AbcCoreAbstract::ObjectHeader &alembic_header, + const Object *const ob, + const char **err_str) const = 0; virtual void readObjectData(Main *bmain, const Alembic::Abc::ISampleSelector &sample_sel) = 0; - DerivedMesh *read_derivedmesh(DerivedMesh *dm, - const Alembic::Abc::ISampleSelector &sample_sel, - int read_flag, - const char **err_str); + virtual DerivedMesh *read_derivedmesh(DerivedMesh *dm, + const Alembic::Abc::ISampleSelector &sample_sel, + int read_flag, + const char **err_str); /** Reads the object matrix and sets up an object transform if animated. */ void setupObjectTransform(const float time); diff --git a/source/blender/alembic/intern/abc_points.cc b/source/blender/alembic/intern/abc_points.cc index d5ecf16b793..3a2ca8a1b47 100644 --- a/source/blender/alembic/intern/abc_points.cc +++ b/source/blender/alembic/intern/abc_points.cc @@ -151,6 +151,23 @@ bool AbcPointsReader::valid() const return m_schema.valid(); } +bool AbcPointsReader::accepts_object_type(const Alembic::AbcCoreAbstract::ObjectHeader &alembic_header, + const Object *const ob, + const char **err_str) const +{ + if (!Alembic::AbcGeom::IPoints::matches(alembic_header)) { + *err_str = "Object type mismatch, Alembic object path pointed to Points when importing, but not any more."; + return false; + } + + if (ob->type != OB_EMPTY) { + *err_str = "Object type mismatch, Alembic object path points to Points."; + return false; + } + + return true; +} + void AbcPointsReader::readObjectData(Main *bmain, const Alembic::Abc::ISampleSelector &sample_sel) { Mesh *mesh = BKE_mesh_add(bmain, m_data_name.c_str()); diff --git a/source/blender/alembic/intern/abc_points.h b/source/blender/alembic/intern/abc_points.h index 1f74351d302..369a802d763 100644 --- a/source/blender/alembic/intern/abc_points.h +++ b/source/blender/alembic/intern/abc_points.h @@ -58,6 +58,9 @@ public: AbcPointsReader(const Alembic::Abc::IObject &object, ImportSettings &settings); bool valid() const; + bool accepts_object_type(const Alembic::AbcCoreAbstract::ObjectHeader &alembic_header, + const Object *const ob, + const char **err_str) const; void readObjectData(Main *bmain, const Alembic::Abc::ISampleSelector &sample_sel); diff --git a/source/blender/alembic/intern/abc_transform.cc b/source/blender/alembic/intern/abc_transform.cc index c48be361877..e2369e80618 100644 --- a/source/blender/alembic/intern/abc_transform.cc +++ b/source/blender/alembic/intern/abc_transform.cc @@ -154,6 +154,23 @@ bool AbcEmptyReader::valid() const return m_schema.valid(); } +bool AbcEmptyReader::accepts_object_type(const Alembic::AbcCoreAbstract::ObjectHeader &alembic_header, + const Object *const ob, + const char **err_str) const +{ + if (!Alembic::AbcGeom::IXform::matches(alembic_header)) { + *err_str = "Object type mismatch, Alembic object path pointed to XForm when importing, but not any more."; + return false; + } + + if (ob->type != OB_EMPTY) { + *err_str = "Object type mismatch, Alembic object path points to XForm."; + return false; + } + + return true; +} + void AbcEmptyReader::readObjectData(Main *bmain, const ISampleSelector &UNUSED(sample_sel)) { m_object = BKE_object_add_only_object(bmain, OB_EMPTY, diff --git a/source/blender/alembic/intern/abc_transform.h b/source/blender/alembic/intern/abc_transform.h index f2e2edf8010..753a4247e9f 100644 --- a/source/blender/alembic/intern/abc_transform.h +++ b/source/blender/alembic/intern/abc_transform.h @@ -68,6 +68,9 @@ public: AbcEmptyReader(const Alembic::Abc::IObject &object, ImportSettings &settings); bool valid() const; + bool accepts_object_type(const Alembic::AbcCoreAbstract::ObjectHeader &alembic_header, + const Object *const ob, + const char **err_str) const; void readObjectData(Main *bmain, const Alembic::Abc::ISampleSelector &sample_sel); }; diff --git a/source/blender/alembic/intern/alembic_capi.cc b/source/blender/alembic/intern/alembic_capi.cc index 52a87d7c165..52864799133 100644 --- a/source/blender/alembic/intern/alembic_capi.cc +++ b/source/blender/alembic/intern/alembic_capi.cc @@ -172,7 +172,7 @@ static bool gather_objects_paths(const IObject &object, ListBase *object_paths) void *abc_path_void = MEM_callocN(sizeof(AlembicObjectPath), "AlembicObjectPath"); AlembicObjectPath *abc_path = static_cast<AlembicObjectPath *>(abc_path_void); - BLI_strncpy(abc_path->path, object.getFullName().c_str(), PATH_MAX); + BLI_strncpy(abc_path->path, object.getFullName().c_str(), sizeof(abc_path->path)); BLI_addtail(object_paths, abc_path); } @@ -359,6 +359,7 @@ bool ABC_export( std::swap(job->settings.frame_start, job->settings.frame_end); } + bool export_ok = false; if (as_background_job) { wmJob *wm_job = WM_jobs_get(CTX_wm_manager(C), CTX_wm_window(C), @@ -381,9 +382,12 @@ bool ABC_export( export_startjob(job, &stop, &do_update, &progress); export_endjob(job); + export_ok = job->export_ok; + + MEM_freeN(job); } - return job->export_ok; + return export_ok; } /* ********************** Import file ********************** */ @@ -542,7 +546,7 @@ static std::pair<bool, AbcObjectReader *> visit_object( AlembicObjectPath *abc_path = static_cast<AlembicObjectPath *>( MEM_callocN(sizeof(AlembicObjectPath), "AlembicObjectPath")); - BLI_strncpy(abc_path->path, full_name.c_str(), PATH_MAX); + BLI_strncpy(abc_path->path, full_name.c_str(), sizeof(abc_path->path)); BLI_addtail(&settings.cache_file->object_paths, abc_path); /* We can now assign this reader as parent for our children. */ @@ -595,6 +599,7 @@ static std::pair<bool, AbcObjectReader *> visit_object( enum { ABC_NO_ERROR = 0, ABC_ARCHIVE_FAIL, + ABC_UNSUPPORTED_HDF5, }; struct ImportJobData { @@ -659,8 +664,12 @@ static void import_startjob(void *user_data, short *stop, short *do_update, floa ArchiveReader *archive = new ArchiveReader(data->filename); if (!archive->valid()) { - delete archive; +#ifndef WITH_ALEMBIC_HDF5 + data->error_code = archive->is_hdf5() ? ABC_UNSUPPORTED_HDF5 : ABC_ARCHIVE_FAIL; +#else data->error_code = ABC_ARCHIVE_FAIL; +#endif + delete archive; return; } @@ -830,6 +839,9 @@ static void import_endjob(void *user_data) case ABC_ARCHIVE_FAIL: WM_report(RPT_ERROR, "Could not open Alembic archive for reading! See console for detail."); break; + case ABC_UNSUPPORTED_HDF5: + WM_report(RPT_ERROR, "Alembic archive in obsolete HDF5 format is not supported."); + break; } WM_main_add_notifier(NC_SCENE | ND_FRAME, data->scene); @@ -864,13 +876,14 @@ bool ABC_import(bContext *C, const char *filepath, float scale, bool is_sequence G.is_break = false; + bool import_ok = false; if (as_background_job) { wmJob *wm_job = WM_jobs_get(CTX_wm_manager(C), - CTX_wm_window(C), - job->scene, - "Alembic Import", - WM_JOB_PROGRESS, - WM_JOB_TYPE_ALEMBIC); + CTX_wm_window(C), + job->scene, + "Alembic Import", + WM_JOB_PROGRESS, + WM_JOB_TYPE_ALEMBIC); /* setup job */ WM_jobs_customdata_set(wm_job, job, import_freejob); @@ -886,9 +899,12 @@ bool ABC_import(bContext *C, const char *filepath, float scale, bool is_sequence import_startjob(job, &stop, &do_update, &progress); import_endjob(job); + import_ok = job->import_ok; + + import_freejob(job); } - return job->import_ok; + return import_ok; } /* ************************************************************************** */ @@ -923,43 +939,13 @@ DerivedMesh *ABC_read_mesh(CacheReader *reader, } const ObjectHeader &header = iobject.getHeader(); - ISampleSelector sample_sel(time); - - if (IPolyMesh::matches(header)) { - if (ob->type != OB_MESH) { - *err_str = "Object type mismatch: object path points to a mesh!"; - return NULL; - } - - return abc_reader->read_derivedmesh(dm, sample_sel, read_flag, err_str); - } - else if (ISubD::matches(header)) { - if (ob->type != OB_MESH) { - *err_str = "Object type mismatch: object path points to a subdivision mesh!"; - return NULL; - } - - return abc_reader->read_derivedmesh(dm, sample_sel, read_flag, err_str); - } - else if (IPoints::matches(header)) { - if (ob->type != OB_MESH) { - *err_str = "Object type mismatch: object path points to a point cloud (requires a mesh object)!"; - return NULL; - } - - return abc_reader->read_derivedmesh(dm, sample_sel, read_flag, err_str); - } - else if (ICurves::matches(header)) { - if (ob->type != OB_CURVE) { - *err_str = "Object type mismatch: object path points to a curve!"; - return NULL; - } - - return abc_reader->read_derivedmesh(dm, sample_sel, read_flag, err_str); + if (!abc_reader->accepts_object_type(header, ob, err_str)) { + /* err_str is set by acceptsObjectType() */ + return NULL; } - *err_str = "Unsupported object type: verify object path"; // or poke developer - return NULL; + ISampleSelector sample_sel(time); + return abc_reader->read_derivedmesh(dm, sample_sel, read_flag, err_str); } /* ************************************************************************** */ @@ -974,6 +960,12 @@ void CacheReader_free(CacheReader *reader) } } +void CacheReader_incref(CacheReader *reader) +{ + AbcObjectReader *abc_reader = reinterpret_cast<AbcObjectReader *>(reader); + abc_reader->incref(); +} + CacheReader *CacheReader_open_alembic_object(AbcArchiveHandle *handle, CacheReader *reader, Object *object, const char *object_path) { if (object_path[0] == '\0') { diff --git a/source/blender/blenkernel/intern/constraint.c b/source/blender/blenkernel/intern/constraint.c index 58ad171ee20..9bc1ce16284 100644 --- a/source/blender/blenkernel/intern/constraint.c +++ b/source/blender/blenkernel/intern/constraint.c @@ -4387,19 +4387,17 @@ static void transformcache_copy(bConstraint *con, bConstraint *srccon) BLI_strncpy(dst->object_path, src->object_path, sizeof(dst->object_path)); dst->cache_file = src->cache_file; - if (dst->cache_file) { - id_us_plus(&dst->cache_file->id); +#ifdef WITH_ALEMBIC + if (dst->reader) { + CacheReader_incref(dst->reader); } +#endif } static void transformcache_free(bConstraint *con) { bTransformCacheConstraint *data = con->data; - if (data->cache_file) { - id_us_min(&data->cache_file->id); - } - if (data->reader) { #ifdef WITH_ALEMBIC CacheReader_free(data->reader); diff --git a/source/blender/blenkernel/intern/object.c b/source/blender/blenkernel/intern/object.c index 6e754755cf3..fbca03c1e07 100644 --- a/source/blender/blenkernel/intern/object.c +++ b/source/blender/blenkernel/intern/object.c @@ -127,6 +127,7 @@ #endif #include "CCGSubSurf.h" +#include "atomic_ops.h" #include "GPU_material.h" @@ -319,19 +320,24 @@ void BKE_object_link_modifiers(struct Object *ob_dst, const struct Object *ob_sr /* free data derived from mesh, called when mesh changes or is freed */ void BKE_object_free_derived_caches(Object *ob) { - /* also serves as signal to remake texspace */ + /* Also serves as signal to remake texspace. + * + * NOTE: This function can be called from threads on different objects + * sharing same data datablock. So we need to ensure atomic nature of + * data modification here. + */ if (ob->type == OB_MESH) { Mesh *me = ob->data; if (me && me->bb) { - me->bb->flag |= BOUNDBOX_DIRTY; + atomic_fetch_and_or_uint32((uint*)&me->bb->flag, BOUNDBOX_DIRTY); } } else if (ELEM(ob->type, OB_SURF, OB_CURVE, OB_FONT)) { Curve *cu = ob->data; if (cu && cu->bb) { - cu->bb->flag |= BOUNDBOX_DIRTY; + atomic_fetch_and_or_uint32((uint*)&cu->bb->flag, BOUNDBOX_DIRTY); } } diff --git a/source/blender/blenlib/intern/threads.c b/source/blender/blenlib/intern/threads.c index 77da3be0600..abf611d1245 100644 --- a/source/blender/blenlib/intern/threads.c +++ b/source/blender/blenlib/intern/threads.c @@ -813,6 +813,11 @@ void BLI_begin_threaded_malloc(void) unsigned int level = atomic_fetch_and_add_u(&thread_levels, 1); if (level == 0) { MEM_set_lock_callback(BLI_lock_malloc_thread, BLI_unlock_malloc_thread); + /* There is a little chance that two threads will meed to acces to a + * scheduler which was not yet created from main thread. which could + * cause scheduler created multiple times. + */ + BLI_task_scheduler_get(); } } diff --git a/source/blender/compositor/operations/COM_PlaneCornerPinOperation.cpp b/source/blender/compositor/operations/COM_PlaneCornerPinOperation.cpp index fb8730c9fa0..d6affa6eee9 100644 --- a/source/blender/compositor/operations/COM_PlaneCornerPinOperation.cpp +++ b/source/blender/compositor/operations/COM_PlaneCornerPinOperation.cpp @@ -29,8 +29,6 @@ #include "BLI_math_color.h" extern "C" { -# include "BLI_jitter.h" - # include "BKE_node.h" } diff --git a/source/blender/compositor/operations/COM_PlaneTrackOperation.cpp b/source/blender/compositor/operations/COM_PlaneTrackOperation.cpp index a56aa0cbaa6..070b7562b2d 100644 --- a/source/blender/compositor/operations/COM_PlaneTrackOperation.cpp +++ b/source/blender/compositor/operations/COM_PlaneTrackOperation.cpp @@ -29,8 +29,6 @@ #include "BLI_math_color.h" extern "C" { -# include "BLI_jitter.h" - # include "BKE_movieclip.h" # include "BKE_node.h" # include "BKE_tracking.h" diff --git a/source/blender/editors/curve/editcurve.c b/source/blender/editors/curve/editcurve.c index 648fe930030..a69264cd012 100644 --- a/source/blender/editors/curve/editcurve.c +++ b/source/blender/editors/curve/editcurve.c @@ -5850,6 +5850,7 @@ static int curve_dissolve_exec(bContext *C, wmOperator *UNUSED(op)) BLI_assert(points_stride + dims == points + (points_len * dims)); float tan_l[3], tan_r[3], error_sq_dummy; + unsigned int error_index_dummy; sub_v3_v3v3(tan_l, bezt_prev->vec[1], bezt_prev->vec[2]); normalize_v3(tan_l); @@ -5860,7 +5861,7 @@ static int curve_dissolve_exec(bContext *C, wmOperator *UNUSED(op)) points, points_len, NULL, dims, FLT_EPSILON, tan_l, tan_r, bezt_prev->vec[2], bezt_next->vec[0], - &error_sq_dummy); + &error_sq_dummy, &error_index_dummy); if (!ELEM(bezt_prev->h2, HD_FREE, HD_ALIGN)) { bezt_prev->h2 = (bezt_prev->h2 == HD_VECT) ? HD_FREE : HD_ALIGN; diff --git a/source/blender/editors/gpencil/drawgpencil.c b/source/blender/editors/gpencil/drawgpencil.c index f091609da49..ecab37c729f 100644 --- a/source/blender/editors/gpencil/drawgpencil.c +++ b/source/blender/editors/gpencil/drawgpencil.c @@ -528,15 +528,15 @@ static void gp_draw_stroke_fill( } else { /* As an initial implementation, we use the OpenGL filled polygon drawing - * here since it's the easiest option to implement for this case. It does - * come with limitations (notably for concave shapes), though it shouldn't - * be much of an issue in most cases. - * - * We keep this legacy implementation around despite now having the high quality - * fills, as this is necessary for keeping everything working nicely for files - * created using old versions of Blender which may have depended on the artifacts - * the old fills created. - */ + * here since it's the easiest option to implement for this case. It does + * come with limitations (notably for concave shapes), though it shouldn't + * be much of an issue in most cases. + * + * We keep this legacy implementation around despite now having the high quality + * fills, as this is necessary for keeping everything working nicely for files + * created using old versions of Blender which may have depended on the artifacts + * the old fills created. + */ bGPDspoint *pt; glBegin(GL_POLYGON); diff --git a/source/blender/editors/gpencil/gpencil_brush.c b/source/blender/editors/gpencil/gpencil_brush.c index ec5a42c23a5..8ddf3a22517 100644 --- a/source/blender/editors/gpencil/gpencil_brush.c +++ b/source/blender/editors/gpencil/gpencil_brush.c @@ -297,9 +297,9 @@ static bool gp_brush_strength_apply( float inf; /* Compute strength of effect - * - We divide the strength by 10, so that users can set "sane" values. - * Otherwise, good default values are in the range of 0.093 - */ + * - We divide the strength by 10, so that users can set "sane" values. + * Otherwise, good default values are in the range of 0.093 + */ inf = gp_brush_influence_calc(gso, radius, co) / 10.0f; /* apply */ diff --git a/source/blender/editors/gpencil/gpencil_paint.c b/source/blender/editors/gpencil/gpencil_paint.c index d6e40377e63..162b9466225 100644 --- a/source/blender/editors/gpencil/gpencil_paint.c +++ b/source/blender/editors/gpencil/gpencil_paint.c @@ -1005,9 +1005,9 @@ static void gp_stroke_newfrombuffer(tGPsdata *p) BLI_strncpy(gps->colorname, palcolor->info, sizeof(gps->colorname)); /* add stroke to frame, usually on tail of the listbase, but if on back is enabled the stroke is added on listbase head - * because the drawing order is inverse and the head stroke is the first to draw. This is very useful for artist - * when drawing the background - */ + * because the drawing order is inverse and the head stroke is the first to draw. This is very useful for artist + * when drawing the background + */ if ((ts->gpencil_flags & GP_TOOL_FLAG_PAINT_ONBACK) && (p->paintmode != GP_PAINTMODE_DRAW_POLY)) { BLI_addhead(&p->gpf->strokes, gps); } diff --git a/source/blender/editors/gpencil/gpencil_utils.c b/source/blender/editors/gpencil/gpencil_utils.c index 76e85f20c36..2b662d04f03 100644 --- a/source/blender/editors/gpencil/gpencil_utils.c +++ b/source/blender/editors/gpencil/gpencil_utils.c @@ -830,8 +830,8 @@ bool gp_smooth_stroke_strength(bGPDstroke *gps, int i, float inf) ptc = &gps->points[after]; /* the optimal value is the corresponding to the interpolation of the strength - * at the distance of point b - */ + * at the distance of point b + */ const float fac = line_point_factor_v3(&ptb->x, &pta->x, &ptc->x); const float optimal = (1.0f - fac) * pta->strength + fac * ptc->strength; diff --git a/source/blender/editors/interface/interface_handlers.c b/source/blender/editors/interface/interface_handlers.c index 2974c2e9304..b50789ff897 100644 --- a/source/blender/editors/interface/interface_handlers.c +++ b/source/blender/editors/interface/interface_handlers.c @@ -6757,6 +6757,7 @@ static bool ui_but_menu(bContext *C, uiBut *but) { uiPopupMenu *pup; uiLayout *layout; + MenuType *mt = WM_menutype_find("WM_MT_button_context", true); bool is_array, is_array_component; uiStringInfo label = {BUT_GET_LABEL, NULL}; @@ -6788,6 +6789,12 @@ static bool ui_but_menu(bContext *C, uiBut *but) /*bool is_idprop = RNA_property_is_idprop(prop);*/ /* XXX does not work as expected, not strictly needed */ bool is_set = RNA_property_is_set(ptr, prop); + /* set the prop and pointer data for python access to the hovered ui element; TODO, index could be supported as well*/ + PointerRNA temp_ptr; + RNA_pointer_create(NULL, &RNA_Property, but->rnaprop, &temp_ptr); + uiLayoutSetContextPointer(layout,"button_prop", &temp_ptr); + uiLayoutSetContextPointer(layout,"button_pointer", ptr); + /* second slower test, saved people finding keyframe items in menus when its not possible */ if (is_anim) is_anim = RNA_property_path_from_ID_check(&but->rnapoin, but->rnaprop); @@ -7003,7 +7010,10 @@ static bool ui_but_menu(bContext *C, uiBut *but) 0, 0, w, UI_UNIT_Y, NULL, 0, 0, 0, 0, ""); UI_but_func_set(but2, popup_add_shortcut_func, but, NULL); } - + + /* Set the operator pointer for python access */ + uiLayoutSetContextPointer(layout,"button_operator", but->opptr); + uiItemS(layout); } @@ -7050,6 +7060,14 @@ static bool ui_but_menu(bContext *C, uiBut *but) } uiItemFullO(layout, "UI_OT_edittranslation_init", NULL, ICON_NONE, NULL, WM_OP_INVOKE_DEFAULT, 0); + mt = WM_menutype_find("WM_MT_button_context", false); + if (mt) { + Menu menu = {NULL}; + menu.layout = uiLayoutColumn(layout, false); + menu.type = mt; + mt->draw(C, &menu); + } + UI_popup_menu_end(C, pup); return true; diff --git a/source/blender/editors/render/render_opengl.c b/source/blender/editors/render/render_opengl.c index 1d0f433ba38..c7ee57240cf 100644 --- a/source/blender/editors/render/render_opengl.c +++ b/source/blender/editors/render/render_opengl.c @@ -38,7 +38,6 @@ #include "BLI_math_color_blend.h" #include "BLI_blenlib.h" #include "BLI_utildefines.h" -#include "BLI_jitter.h" #include "BLI_threads.h" #include "BLI_task.h" @@ -257,10 +256,8 @@ static void screen_opengl_views_setup(OGLRender *oglrender) } } - BLI_lock_thread(LOCK_DRAW_IMAGE); if (!(is_multiview && BKE_scene_multiview_is_stereo3d(rd))) oglrender->iuser.flag &= ~IMA_SHOW_STEREO; - BLI_unlock_thread(LOCK_DRAW_IMAGE); /* will only work for non multiview correctly */ if (v3d) { @@ -874,7 +871,7 @@ static bool screen_opengl_render_anim_initialize(bContext *C, wmOperator *op) typedef struct WriteTaskData { RenderResult *rr; - int cfra; + Scene tmp_scene; } WriteTaskData; static void write_result_func(TaskPool * __restrict pool, @@ -883,10 +880,10 @@ static void write_result_func(TaskPool * __restrict pool, { OGLRender *oglrender = (OGLRender *) BLI_task_pool_userdata(pool); WriteTaskData *task_data = (WriteTaskData *) task_data_v; - Scene *scene = oglrender->scene; + Scene *scene = &task_data->tmp_scene; RenderResult *rr = task_data->rr; const bool is_movie = BKE_imtype_is_movie(scene->r.im_format.imtype); - const int cfra = task_data->cfra; + const int cfra = scene->r.cfra; bool ok; /* Don't attempt to write if we've got an error. */ if (!oglrender->pool_ok) { @@ -908,13 +905,11 @@ static void write_result_func(TaskPool * __restrict pool, * This is because underlying calls do not use r.cfra but use scene * for that. */ - Scene tmp_scene = *scene; - tmp_scene.r.cfra = cfra; if (is_movie) { ok = RE_WriteRenderViewsMovie(&reports, rr, - &tmp_scene, - &tmp_scene.r, + scene, + &scene->r, oglrender->mh, oglrender->movie_ctx_arr, oglrender->totvideos, @@ -934,8 +929,8 @@ static void write_result_func(TaskPool * __restrict pool, true, NULL); - BKE_render_result_stamp_info(&tmp_scene, tmp_scene.camera, rr, false); - ok = RE_WriteRenderViewsImage(NULL, rr, &tmp_scene, true, name); + BKE_render_result_stamp_info(scene, scene->camera, rr, false); + ok = RE_WriteRenderViewsImage(NULL, rr, scene, true, name); if (!ok) { BKE_reportf(&reports, RPT_ERROR, @@ -974,7 +969,7 @@ static bool schedule_write_result(OGLRender *oglrender, RenderResult *rr) Scene *scene = oglrender->scene; WriteTaskData *task_data = MEM_mallocN(sizeof(WriteTaskData), "write task data"); task_data->rr = rr; - task_data->cfra = scene->r.cfra; + task_data->tmp_scene = *scene; BLI_mutex_lock(&oglrender->task_mutex); oglrender->num_scheduled_frames++; if (oglrender->num_scheduled_frames > MAX_SCHEDULED_FRAMES) { diff --git a/source/blender/editors/space_view3d/drawobject.c b/source/blender/editors/space_view3d/drawobject.c index 0436f1335d8..61dd2d7c912 100644 --- a/source/blender/editors/space_view3d/drawobject.c +++ b/source/blender/editors/space_view3d/drawobject.c @@ -867,7 +867,7 @@ void view3d_cached_text_draw_add(const float co[3], memcpy(vos->str, str, alloc_len); } -void view3d_cached_text_draw_end(View3D *v3d, ARegion *ar, bool depth_write, float mat[4][4]) +void view3d_cached_text_draw_end(View3D *v3d, ARegion *ar, bool depth_write) { RegionView3D *rv3d = ar->regiondata; ViewCachedString *vos; @@ -877,9 +877,6 @@ void view3d_cached_text_draw_end(View3D *v3d, ARegion *ar, bool depth_write, flo /* project first and test */ for (vos = g_v3d_strings[g_v3d_string_level]; vos; vos = vos->next) { - if (mat && !(vos->flag & V3D_CACHE_TEXT_WORLDSPACE)) - mul_m4_v3(mat, vos->vec); - if (ED_view3d_project_short_ex(ar, (vos->flag & V3D_CACHE_TEXT_GLOBALSPACE) ? rv3d->persmat : rv3d->persmatob, (vos->flag & V3D_CACHE_TEXT_LOCALCLIP) != 0, @@ -7826,7 +7823,7 @@ void draw_object(Scene *scene, ARegion *ar, View3D *v3d, Base *base, const short draw_new_particle_system(scene, v3d, rv3d, base, psys, dt, dflag); } invert_m4_m4(ob->imat, ob->obmat); - view3d_cached_text_draw_end(v3d, ar, 0, NULL); + view3d_cached_text_draw_end(v3d, ar, 0); glMultMatrixf(ob->obmat); @@ -8001,7 +7998,7 @@ void draw_object(Scene *scene, ARegion *ar, View3D *v3d, Base *base, const short /* return warning, this is cached text draw */ invert_m4_m4(ob->imat, ob->obmat); - view3d_cached_text_draw_end(v3d, ar, 1, NULL); + view3d_cached_text_draw_end(v3d, ar, 1); /* return warning, clear temp flag */ v3d->flag2 &= ~V3D_SHOW_SOLID_MATCAP; diff --git a/source/blender/editors/space_view3d/drawsimdebug.c b/source/blender/editors/space_view3d/drawsimdebug.c index 9414d39467d..3f23d4aa09a 100644 --- a/source/blender/editors/space_view3d/drawsimdebug.c +++ b/source/blender/editors/space_view3d/drawsimdebug.c @@ -171,7 +171,7 @@ void draw_sim_debug_data(Scene *UNUSED(scene), View3D *v3d, ARegion *ar) view3d_cached_text_draw_begin(); draw_sim_debug_elements(_sim_debug_data, imat); - view3d_cached_text_draw_end(v3d, ar, false, NULL); + view3d_cached_text_draw_end(v3d, ar, false); glPopMatrix(); diff --git a/source/blender/editors/space_view3d/view3d_draw.c b/source/blender/editors/space_view3d/view3d_draw.c index 3fb2761d40e..8f2ea86f836 100644 --- a/source/blender/editors/space_view3d/view3d_draw.c +++ b/source/blender/editors/space_view3d/view3d_draw.c @@ -2393,43 +2393,13 @@ void ED_view3d_draw_depth_gpencil(Scene *scene, ARegion *ar, View3D *v3d) } -void ED_view3d_draw_depth(Scene *scene, ARegion *ar, View3D *v3d, bool alphaoverride) +static void view3d_draw_depth_loop(Scene *scene, ARegion *ar, View3D *v3d) { - RegionView3D *rv3d = ar->regiondata; Base *base; - short zbuf = v3d->zbuf; - short flag = v3d->flag; - float glalphaclip = U.glalphaclip; - int obcenter_dia = U.obcenter_dia; + /* no need for color when drawing depth buffer */ const short dflag_depth = DRAW_CONSTCOLOR; - /* temp set drawtype to solid */ - - /* Setting these temporarily is not nice */ - v3d->flag &= ~V3D_SELECT_OUTLINE; - U.glalphaclip = alphaoverride ? 0.5f : glalphaclip; /* not that nice but means we wont zoom into billboards */ - U.obcenter_dia = 0; - - view3d_winmatrix_set(ar, v3d, NULL); - view3d_viewmatrix_set(scene, v3d, rv3d); /* note: calls BKE_object_where_is_calc for camera... */ - - mul_m4_m4m4(rv3d->persmat, rv3d->winmat, rv3d->viewmat); - invert_m4_m4(rv3d->persinv, rv3d->persmat); - invert_m4_m4(rv3d->viewinv, rv3d->viewmat); - - glClear(GL_DEPTH_BUFFER_BIT); - - glLoadMatrixf(rv3d->viewmat); - - if (rv3d->rflag & RV3D_CLIPPING) { - ED_view3d_clipping_set(rv3d); - } - /* get surface depth without bias */ - rv3d->rflag |= RV3D_ZOFFSET_DISABLED; - v3d->zbuf = true; - glEnable(GL_DEPTH_TEST); - /* draw set first */ if (scene->set) { Scene *sce_iter; @@ -2503,7 +2473,44 @@ void ED_view3d_draw_depth(Scene *scene, ARegion *ar, View3D *v3d, bool alphaover glDepthMask(mask_orig); } +} + +void ED_view3d_draw_depth(Scene *scene, ARegion *ar, View3D *v3d, bool alphaoverride) +{ + RegionView3D *rv3d = ar->regiondata; + short zbuf = v3d->zbuf; + short flag = v3d->flag; + float glalphaclip = U.glalphaclip; + int obcenter_dia = U.obcenter_dia; + /* temp set drawtype to solid */ + + /* Setting these temporarily is not nice */ + v3d->flag &= ~V3D_SELECT_OUTLINE; + U.glalphaclip = alphaoverride ? 0.5f : glalphaclip; /* not that nice but means we wont zoom into billboards */ + U.obcenter_dia = 0; + + view3d_winmatrix_set(ar, v3d, NULL); + view3d_viewmatrix_set(scene, v3d, rv3d); /* note: calls BKE_object_where_is_calc for camera... */ + + mul_m4_m4m4(rv3d->persmat, rv3d->winmat, rv3d->viewmat); + invert_m4_m4(rv3d->persinv, rv3d->persmat); + invert_m4_m4(rv3d->viewinv, rv3d->viewmat); + + glClear(GL_DEPTH_BUFFER_BIT); + glLoadMatrixf(rv3d->viewmat); + + if (rv3d->rflag & RV3D_CLIPPING) { + ED_view3d_clipping_set(rv3d); + } + /* get surface depth without bias */ + rv3d->rflag |= RV3D_ZOFFSET_DISABLED; + + v3d->zbuf = true; + glEnable(GL_DEPTH_TEST); + + view3d_draw_depth_loop(scene, ar, v3d); + if (rv3d->rflag & RV3D_CLIPPING) { ED_view3d_clipping_disable(); } diff --git a/source/blender/editors/space_view3d/view3d_edit.c b/source/blender/editors/space_view3d/view3d_edit.c index f07727f8118..4e3f279e12e 100644 --- a/source/blender/editors/space_view3d/view3d_edit.c +++ b/source/blender/editors/space_view3d/view3d_edit.c @@ -85,6 +85,8 @@ #include "view3d_intern.h" /* own include */ +static bool view3d_ensure_persp(struct View3D *v3d, ARegion *ar); + bool ED_view3d_offset_lock_check(const View3D *v3d, const RegionView3D *rv3d) { return (rv3d->persp != RV3D_CAMOB) && (v3d->ob_centre_cursor || v3d->ob_centre); @@ -697,16 +699,68 @@ static bool view3d_orbit_calc_center(bContext *C, float r_dyn_ofs[3]) return is_set; } +enum eViewOpsOrbit { + VIEWOPS_ORBIT_SELECT = (1 << 0), + VIEWOPS_ORBIT_DEPTH = (1 << 1), +}; + +static enum eViewOpsOrbit viewops_orbit_mode_ex(bool use_select, bool use_depth) +{ + enum eViewOpsOrbit flag = 0; + if (use_select) { + flag |= VIEWOPS_ORBIT_SELECT; + } + if (use_depth) { + flag |= VIEWOPS_ORBIT_DEPTH; + } + + return flag; +} + +static enum eViewOpsOrbit viewops_orbit_mode(void) +{ + return viewops_orbit_mode_ex( + (U.uiflag & USER_ORBIT_SELECTION) != 0, + (U.uiflag & USER_ZBUF_ORBIT) != 0); +} + /** * Calculate the values for #ViewOpsData */ -static void viewops_data_create_ex(bContext *C, wmOperator *op, const wmEvent *event, - const bool use_orbit_select, - const bool use_orbit_zbuf) +static void viewops_data_create_ex( + bContext *C, wmOperator *op, const wmEvent *event, + bool switch_from_camera, enum eViewOpsOrbit orbit_mode) { ViewOpsData *vod = op->customdata; RegionView3D *rv3d = vod->rv3d; + /* we need the depth info before changing any viewport options */ + if (orbit_mode & VIEWOPS_ORBIT_DEPTH) { + float fallback_depth_pt[3]; + + view3d_operator_needs_opengl(C); /* needed for zbuf drawing */ + + negate_v3_v3(fallback_depth_pt, rv3d->ofs); + + vod->use_dyn_ofs = ED_view3d_autodist( + vod->scene, vod->ar, vod->v3d, + event->mval, vod->dyn_ofs, true, fallback_depth_pt); + } + else { + vod->use_dyn_ofs = false; + } + + if (switch_from_camera) { + /* switch from camera view when: */ + if (view3d_ensure_persp(vod->v3d, vod->ar)) { + /* If we're switching from camera view to the perspective one, + * need to tag viewport update, so camera vuew and borders + * are properly updated. + */ + ED_region_tag_redraw(vod->ar); + } + } + /* set the view from the camera, if view locking is enabled. * we may want to make this optional but for now its needed always */ ED_view3d_camera_lock_init(vod->v3d, vod->rv3d); @@ -718,28 +772,19 @@ static void viewops_data_create_ex(bContext *C, wmOperator *op, const wmEvent *e vod->origx = vod->oldx = event->x; vod->origy = vod->oldy = event->y; vod->origkey = event->type; /* the key that triggered the operator. */ - vod->use_dyn_ofs = false; copy_v3_v3(vod->ofs, rv3d->ofs); - if (use_orbit_select) { - - vod->use_dyn_ofs = true; - - view3d_orbit_calc_center(C, vod->dyn_ofs); - - negate_v3(vod->dyn_ofs); + if (orbit_mode & VIEWOPS_ORBIT_SELECT) { + float ofs[3]; + if (view3d_orbit_calc_center(C, ofs) || (vod->use_dyn_ofs == false)) { + vod->use_dyn_ofs = true; + negate_v3_v3(vod->dyn_ofs, ofs); + orbit_mode &= ~VIEWOPS_ORBIT_DEPTH; + } } - else if (use_orbit_zbuf) { - Scene *scene = CTX_data_scene(C); - float fallback_depth_pt[3]; - - view3d_operator_needs_opengl(C); /* needed for zbuf drawing */ - - negate_v3_v3(fallback_depth_pt, rv3d->ofs); - if ((vod->use_dyn_ofs = ED_view3d_autodist(scene, vod->ar, vod->v3d, - event->mval, vod->dyn_ofs, true, fallback_depth_pt))) - { + if (orbit_mode & VIEWOPS_ORBIT_DEPTH) { + if (vod->use_dyn_ofs) { if (rv3d->is_persp) { float my_origin[3]; /* original G.vd->ofs */ float my_pivot[3]; /* view */ @@ -808,12 +853,10 @@ static void viewops_data_create_ex(bContext *C, wmOperator *op, const wmEvent *e rv3d->rflag |= RV3D_NAVIGATING; } -static void viewops_data_create(bContext *C, wmOperator *op, const wmEvent *event) +static void viewops_data_create(bContext *C, wmOperator *op, const wmEvent *event, bool switch_from_camera) { - viewops_data_create_ex( - C, op, event, - (U.uiflag & USER_ORBIT_SELECTION) != 0, - (U.uiflag & USER_ZBUF_ORBIT) != 0); + enum eViewOpsOrbit orbit_mode = viewops_orbit_mode(); + viewops_data_create_ex(C, op, event, switch_from_camera, orbit_mode); } static void viewops_data_free(bContext *C, wmOperator *op) @@ -1219,16 +1262,7 @@ static int viewrotate_invoke(bContext *C, wmOperator *op, const wmEvent *event) ED_view3d_smooth_view_force_finish(C, vod->v3d, vod->ar); - /* switch from camera view when: */ - if (view3d_ensure_persp(vod->v3d, vod->ar)) { - /* If we're switching from camera view to the perspective one, - * need to tag viewport update, so camera vuew and borders - * are properly updated. - */ - ED_region_tag_redraw(vod->ar); - } - - viewops_data_create(C, op, event); + viewops_data_create(C, op, event, true); if (ELEM(event->type, MOUSEPAN, MOUSEROTATE)) { /* Rotate direction we keep always same */ @@ -1637,8 +1671,9 @@ static int ndof_orbit_invoke(bContext *C, wmOperator *op, const wmEvent *event) const wmNDOFMotionData *ndof = event->customdata; viewops_data_alloc(C, op); - viewops_data_create_ex(C, op, event, - (U.uiflag & USER_ORBIT_SELECTION) != 0, false); + viewops_data_create_ex( + C, op, event, + viewops_orbit_mode_ex((U.uiflag & USER_ORBIT_SELECTION) != 0, false), false); vod = op->customdata; ED_view3d_smooth_view_force_finish(C, vod->v3d, vod->ar); @@ -1705,8 +1740,9 @@ static int ndof_orbit_zoom_invoke(bContext *C, wmOperator *op, const wmEvent *ev const wmNDOFMotionData *ndof = event->customdata; viewops_data_alloc(C, op); - viewops_data_create_ex(C, op, event, - (U.uiflag & USER_ORBIT_SELECTION) != 0, false); + viewops_data_create_ex( + C, op, event, + viewops_orbit_mode_ex((U.uiflag & USER_ORBIT_SELECTION) != 0, false), false); vod = op->customdata; @@ -2020,7 +2056,7 @@ static int viewmove_invoke(bContext *C, wmOperator *op, const wmEvent *event) /* makes op->customdata */ viewops_data_alloc(C, op); - viewops_data_create(C, op, event); + viewops_data_create(C, op, event, false); vod = op->customdata; ED_view3d_smooth_view_force_finish(C, vod->v3d, vod->ar); @@ -2501,7 +2537,7 @@ static int viewzoom_invoke(bContext *C, wmOperator *op, const wmEvent *event) /* makes op->customdata */ viewops_data_alloc(C, op); - viewops_data_create(C, op, event); + viewops_data_create(C, op, event, false); vod = op->customdata; ED_view3d_smooth_view_force_finish(C, vod->v3d, vod->ar); @@ -2774,7 +2810,7 @@ static int viewdolly_invoke(bContext *C, wmOperator *op, const wmEvent *event) ED_region_tag_redraw(vod->ar); } - viewops_data_create(C, op, event); + viewops_data_create(C, op, event, false); /* if one or the other zoom position aren't set, set from event */ @@ -4298,7 +4334,7 @@ static int viewroll_invoke(bContext *C, wmOperator *op, const wmEvent *event) else { /* makes op->customdata */ viewops_data_alloc(C, op); - viewops_data_create(C, op, event); + viewops_data_create(C, op, event, false); vod = op->customdata; ED_view3d_smooth_view_force_finish(C, vod->v3d, vod->ar); @@ -4375,7 +4411,7 @@ static int viewpan_invoke(bContext *C, wmOperator *op, const wmEvent *event) else if (pandir == V3D_VIEW_PANDOWN) { y = 25; } viewops_data_alloc(C, op); - viewops_data_create(C, op, event); + viewops_data_create(C, op, event, false); ViewOpsData *vod = op->customdata; viewmove_apply(vod, vod->oldx + x, vod->oldy + y); diff --git a/source/blender/editors/space_view3d/view3d_intern.h b/source/blender/editors/space_view3d/view3d_intern.h index c2b8d1f8bda..7a106a27833 100644 --- a/source/blender/editors/space_view3d/view3d_intern.h +++ b/source/blender/editors/space_view3d/view3d_intern.h @@ -154,7 +154,7 @@ void view3d_cached_text_draw_begin(void); void view3d_cached_text_draw_add(const float co[3], const char *str, const size_t str_len, short xoffs, short flag, const unsigned char col[4]); -void view3d_cached_text_draw_end(View3D *v3d, ARegion *ar, bool depth_write, float mat[4][4]); +void view3d_cached_text_draw_end(View3D *v3d, ARegion *ar, bool depth_write); bool check_object_draw_texture(struct Scene *scene, struct View3D *v3d, const char drawtype); diff --git a/source/blender/freestyle/intern/application/AppView.cpp b/source/blender/freestyle/intern/application/AppView.cpp index c331d1de9c9..9b1b02c8ee2 100644 --- a/source/blender/freestyle/intern/application/AppView.cpp +++ b/source/blender/freestyle/intern/application/AppView.cpp @@ -22,12 +22,6 @@ * \ingroup freestyle */ -/* This header file needs to be included first, in order to avoid a - compilation with MinGW (see the commit log of revision 28253) */ -extern "C" { -#include "BLI_jitter.h" -} - #include <iostream> #include "Controller.h" diff --git a/source/blender/makesdna/DNA_cachefile_types.h b/source/blender/makesdna/DNA_cachefile_types.h index 46b1adf2725..a353c94ae64 100644 --- a/source/blender/makesdna/DNA_cachefile_types.h +++ b/source/blender/makesdna/DNA_cachefile_types.h @@ -47,10 +47,12 @@ enum { CACHEFILE_KEYFRAME_DRAWN = (1 << 0), }; +/* Representation of an object's path inside the Alembic file. + * Note that this is not a file path. */ typedef struct AlembicObjectPath { struct AlembicObjectPath *next, *prev; - char path[1024]; /* 1024 = FILE_MAX, might use PATH_MAX in the future. */ + char path[4096]; } AlembicObjectPath; typedef struct CacheFile { diff --git a/source/blender/nodes/composite/nodes/node_composite_bilateralblur.c b/source/blender/nodes/composite/nodes/node_composite_bilateralblur.c index 2ad097013ef..fde7dccb4ac 100644 --- a/source/blender/nodes/composite/nodes/node_composite_bilateralblur.c +++ b/source/blender/nodes/composite/nodes/node_composite_bilateralblur.c @@ -47,6 +47,7 @@ static void node_composit_init_bilateralblur(bNodeTree *UNUSED(ntree), bNode *no { NodeBilateralBlurData *nbbd = MEM_callocN(sizeof(NodeBilateralBlurData), "node bilateral blur data"); node->storage = nbbd; + nbbd->iter = 1; nbbd->sigma_color = 0.3; nbbd->sigma_space = 5.0; } diff --git a/source/blender/nodes/composite/nodes/node_composite_directionalblur.c b/source/blender/nodes/composite/nodes/node_composite_directionalblur.c index 6eb27a228ad..336eb3409ff 100644 --- a/source/blender/nodes/composite/nodes/node_composite_directionalblur.c +++ b/source/blender/nodes/composite/nodes/node_composite_directionalblur.c @@ -46,6 +46,7 @@ static void node_composit_init_dblur(bNodeTree *UNUSED(ntree), bNode *node) { NodeDBlurData *ndbd = MEM_callocN(sizeof(NodeDBlurData), "node dblur data"); node->storage = ndbd; + ndbd->iter = 1; ndbd->center_x = 0.5; ndbd->center_y = 0.5; } diff --git a/source/blender/windowmanager/intern/wm_files.c b/source/blender/windowmanager/intern/wm_files.c index 028355f9af3..187c1193ec6 100644 --- a/source/blender/windowmanager/intern/wm_files.c +++ b/source/blender/windowmanager/intern/wm_files.c @@ -724,7 +724,7 @@ int wm_homefile_read( if (filepath_startup_override != NULL) { /* pass */ } - else if (app_template_override) { + else if (app_template_override && app_template_override[0]) { app_template = app_template_override; } else if (!use_factory_settings && U.app_template[0]) { |