Welcome to mirror list, hosted at ThFree Co, Russian Federation.

git.blender.org/blender.git - Unnamed repository; edit this file 'description' to name the repository.
summaryrefslogtreecommitdiff
diff options
context:
space:
mode:
Diffstat (limited to 'source/blender/blenkernel')
-rw-r--r--source/blender/blenkernel/BKE_anim_data.h4
-rw-r--r--source/blender/blenkernel/BKE_attribute.h4
-rw-r--r--source/blender/blenkernel/BKE_blender_version.h2
-rw-r--r--source/blender/blenkernel/BKE_collection.h1
-rw-r--r--source/blender/blenkernel/BKE_editmesh.h35
-rw-r--r--source/blender/blenkernel/BKE_gpencil.h17
-rw-r--r--source/blender/blenkernel/BKE_mesh.h4
-rw-r--r--source/blender/blenkernel/BKE_mesh_types.h1
-rw-r--r--source/blender/blenkernel/BKE_node.h21
-rw-r--r--source/blender/blenkernel/BKE_node_ui_storage.hh133
-rw-r--r--source/blender/blenkernel/BKE_object.h8
-rw-r--r--source/blender/blenkernel/BKE_pointcache.h2
-rw-r--r--source/blender/blenkernel/BKE_scene.h8
-rw-r--r--source/blender/blenkernel/BKE_studiolight.h2
-rw-r--r--source/blender/blenkernel/BKE_undo_system.h7
-rw-r--r--source/blender/blenkernel/CMakeLists.txt9
-rw-r--r--source/blender/blenkernel/intern/DerivedMesh.cc2
-rw-r--r--source/blender/blenkernel/intern/action.c38
-rw-r--r--source/blender/blenkernel/intern/action_test.cc144
-rw-r--r--source/blender/blenkernel/intern/anim_data.c38
-rw-r--r--source/blender/blenkernel/intern/appdir.c7
-rw-r--r--source/blender/blenkernel/intern/armature.c2
-rw-r--r--source/blender/blenkernel/intern/armature_deform.c1
-rw-r--r--source/blender/blenkernel/intern/armature_update.c14
-rw-r--r--source/blender/blenkernel/intern/blendfile.c2
-rw-r--r--source/blender/blenkernel/intern/bvhutils.cc4
-rw-r--r--source/blender/blenkernel/intern/cachefile.c2
-rw-r--r--source/blender/blenkernel/intern/cloth.c2
-rw-r--r--source/blender/blenkernel/intern/collection.c2
-rw-r--r--source/blender/blenkernel/intern/crazyspace.c3
-rw-r--r--source/blender/blenkernel/intern/dynamicpaint.c14
-rw-r--r--source/blender/blenkernel/intern/editmesh.c17
-rw-r--r--source/blender/blenkernel/intern/editmesh_tangent.c1
-rw-r--r--source/blender/blenkernel/intern/fluid.c10
-rw-r--r--source/blender/blenkernel/intern/gpencil.c54
-rw-r--r--source/blender/blenkernel/intern/ipo.c26
-rw-r--r--source/blender/blenkernel/intern/lattice_deform.c2
-rw-r--r--source/blender/blenkernel/intern/layer_utils.c1
-rw-r--r--source/blender/blenkernel/intern/lib_id.c7
-rw-r--r--source/blender/blenkernel/intern/mesh_boolean_convert.cc43
-rw-r--r--source/blender/blenkernel/intern/mesh_evaluate.cc (renamed from source/blender/blenkernel/intern/mesh_evaluate.c)64
-rw-r--r--source/blender/blenkernel/intern/mesh_mapping.c2
-rw-r--r--source/blender/blenkernel/intern/mesh_normals.cc (renamed from source/blender/blenkernel/intern/mesh_normals.c)301
-rw-r--r--source/blender/blenkernel/intern/nla.c21
-rw-r--r--source/blender/blenkernel/intern/node.cc95
-rw-r--r--source/blender/blenkernel/intern/node_ui_storage.cc169
-rw-r--r--source/blender/blenkernel/intern/object.c55
-rw-r--r--source/blender/blenkernel/intern/object_update.c23
-rw-r--r--source/blender/blenkernel/intern/particle.c2
-rw-r--r--source/blender/blenkernel/intern/pbvh.c2
-rw-r--r--source/blender/blenkernel/intern/pointcache.c4
-rw-r--r--source/blender/blenkernel/intern/scene.c49
-rw-r--r--source/blender/blenkernel/intern/screen.c6
-rw-r--r--source/blender/blenkernel/intern/softbody.c2
-rw-r--r--source/blender/blenkernel/intern/spline_base.cc4
-rw-r--r--source/blender/blenkernel/intern/spline_nurbs.cc5
-rw-r--r--source/blender/blenkernel/intern/studiolight.c2
-rw-r--r--source/blender/blenkernel/intern/tracking_region_tracker.c2
-rw-r--r--source/blender/blenkernel/intern/undo_system.c29
59 files changed, 792 insertions, 739 deletions
diff --git a/source/blender/blenkernel/BKE_anim_data.h b/source/blender/blenkernel/BKE_anim_data.h
index 6c07708b5ef..14ab9f21424 100644
--- a/source/blender/blenkernel/BKE_anim_data.h
+++ b/source/blender/blenkernel/BKE_anim_data.h
@@ -50,8 +50,8 @@ bool id_can_have_animdata(const struct ID *id);
/* Get AnimData from the given ID-block */
struct AnimData *BKE_animdata_from_id(struct ID *id);
-/* Add AnimData to the given ID-block */
-struct AnimData *BKE_animdata_add_id(struct ID *id);
+/* Ensure AnimData is present in the ID-block (when supported). */
+struct AnimData *BKE_animdata_ensure_id(struct ID *id);
/* Set active action used by AnimData from the given ID-block */
bool BKE_animdata_set_action(struct ReportList *reports, struct ID *id, struct bAction *act);
diff --git a/source/blender/blenkernel/BKE_attribute.h b/source/blender/blenkernel/BKE_attribute.h
index 6a1f1feb14f..5fda30224c6 100644
--- a/source/blender/blenkernel/BKE_attribute.h
+++ b/source/blender/blenkernel/BKE_attribute.h
@@ -39,8 +39,8 @@ struct ReportList;
/* Attribute.domain */
/**
- * \warning: Careful when changing existing items. Arrays may be initialized from this (e.g.
- * #DATASET_layout_hierarchy).
+ * \warning Careful when changing existing items.
+ * Arrays may be initialized from this (e.g. #DATASET_layout_hierarchy).
*/
typedef enum AttributeDomain {
ATTR_DOMAIN_AUTO = -1, /* Use for nodes to choose automatically based on other data. */
diff --git a/source/blender/blenkernel/BKE_blender_version.h b/source/blender/blenkernel/BKE_blender_version.h
index 9d286b94b04..dffd70c077f 100644
--- a/source/blender/blenkernel/BKE_blender_version.h
+++ b/source/blender/blenkernel/BKE_blender_version.h
@@ -39,7 +39,7 @@ extern "C" {
/* Blender file format version. */
#define BLENDER_FILE_VERSION BLENDER_VERSION
-#define BLENDER_FILE_SUBVERSION 8
+#define BLENDER_FILE_SUBVERSION 11
/* Minimum Blender version that supports reading file written with the current
* version. Older Blender versions will test this and show a warning if the file
diff --git a/source/blender/blenkernel/BKE_collection.h b/source/blender/blenkernel/BKE_collection.h
index f47cdf32ca0..0326386e5c1 100644
--- a/source/blender/blenkernel/BKE_collection.h
+++ b/source/blender/blenkernel/BKE_collection.h
@@ -76,6 +76,7 @@ struct Collection *BKE_collection_duplicate(struct Main *bmain,
/* Master Collection for Scene */
+#define BKE_SCENE_COLLECTION_NAME "Scene Collection"
struct Collection *BKE_collection_master_add(void);
/* Collection Objects */
diff --git a/source/blender/blenkernel/BKE_editmesh.h b/source/blender/blenkernel/BKE_editmesh.h
index 9112877b5a3..ce7df62389f 100644
--- a/source/blender/blenkernel/BKE_editmesh.h
+++ b/source/blender/blenkernel/BKE_editmesh.h
@@ -24,7 +24,7 @@
* only concerned with low level operations on the #BMEditMesh structure.
*/
-#include "BKE_customdata.h"
+#include "DNA_customdata_types.h"
#include "bmesh.h"
#ifdef __cplusplus
@@ -44,34 +44,39 @@ struct Scene;
/**
* This structure is used for mesh edit-mode.
*
- * through this, you get access to both the edit #BMesh,
- * its tessellation, and various stuff that doesn't belong in the BMesh
- * struct itself.
+ * Through this, you get access to both the edit #BMesh, its tessellation,
+ * and various data that doesn't belong in the #BMesh struct itself
+ * (mostly related to mesh evaluation).
*
- * the entire derivedmesh and modifier system works with this structure,
- * and not BMesh. Mesh->edit_bmesh stores a pointer to this structure. */
+ * The entire modifier system works with this structure, and not #BMesh.
+ * #Mesh.edit_bmesh stores a pointer to this structure. */
typedef struct BMEditMesh {
struct BMesh *bm;
- /* we store tessellations as triplets of three loops,
- * which each define a triangle. */
+ /**
+ * Face triangulation (tessellation) is stored as triplets of three loops,
+ * which each define a triangle.
+ *
+ * \see #MLoopTri as the documentation gives useful hints that apply to this data too.
+ */
struct BMLoop *(*looptris)[3];
int tottri;
struct Mesh *mesh_eval_final, *mesh_eval_cage;
- /** Cached cage bounding box for selection. */
+ /** Cached cage bounding box of `mesh_eval_cage` for selection. */
struct BoundBox *bb_cage;
/** Evaluated mesh data-mask. */
CustomData_MeshMasks lastDataMask;
- /* Selection mode. */
+ /** Selection mode (#SCE_SELECT_VERTEX, #SCE_SELECT_EDGE & #SCE_SELECT_FACE). */
short selectmode;
+ /** The active material (assigned to newly created faces). */
short mat_nr;
- /* Temp variables for x-mirror editing. */
- int mirror_cdlayer; /* -1 is invalid */
+ /** Temp variables for x-mirror editing (-1 when the layer does not exist). */
+ int mirror_cdlayer;
/**
* ID data is older than edit-mode data.
@@ -94,11 +99,11 @@ void BKE_editmesh_looptri_and_normals_calc_with_partial(BMEditMesh *em,
void BKE_editmesh_looptri_and_normals_calc(BMEditMesh *em);
-BMEditMesh *BKE_editmesh_create(BMesh *bm, const bool do_tessellate);
+BMEditMesh *BKE_editmesh_create(BMesh *bm);
BMEditMesh *BKE_editmesh_copy(BMEditMesh *em);
BMEditMesh *BKE_editmesh_from_object(struct Object *ob);
-void BKE_editmesh_free_derivedmesh(BMEditMesh *em);
-void BKE_editmesh_free(BMEditMesh *em);
+void BKE_editmesh_free_derived_caches(BMEditMesh *em);
+void BKE_editmesh_free_data(BMEditMesh *em);
float (*BKE_editmesh_vert_coords_alloc(struct Depsgraph *depsgraph,
struct BMEditMesh *em,
diff --git a/source/blender/blenkernel/BKE_gpencil.h b/source/blender/blenkernel/BKE_gpencil.h
index 657e66729e1..c11c34cb312 100644
--- a/source/blender/blenkernel/BKE_gpencil.h
+++ b/source/blender/blenkernel/BKE_gpencil.h
@@ -282,20 +282,25 @@ bool BKE_gpencil_from_image(struct SpaceImage *sima,
const float size,
const bool mask);
-/* Iterator */
+/* Iterators */
/* frame & stroke are NULL if it is a layer callback. */
typedef void (*gpIterCb)(struct bGPDlayer *layer,
struct bGPDframe *frame,
struct bGPDstroke *stroke,
void *thunk);
-void BKE_gpencil_visible_stroke_iter(struct ViewLayer *view_layer,
- struct Object *ob,
+void BKE_gpencil_visible_stroke_iter(struct bGPdata *gpd,
gpIterCb layer_cb,
gpIterCb stroke_cb,
- void *thunk,
- bool do_onion,
- int cfra);
+ void *thunk);
+
+void BKE_gpencil_visible_stroke_advanced_iter(struct ViewLayer *view_layer,
+ struct Object *ob,
+ gpIterCb layer_cb,
+ gpIterCb stroke_cb,
+ void *thunk,
+ bool do_onion,
+ int cfra);
extern void (*BKE_gpencil_batch_cache_dirty_tag_cb)(struct bGPdata *gpd);
extern void (*BKE_gpencil_batch_cache_free_cb)(struct bGPdata *gpd);
diff --git a/source/blender/blenkernel/BKE_mesh.h b/source/blender/blenkernel/BKE_mesh.h
index 8d76a025e87..12560ebed7b 100644
--- a/source/blender/blenkernel/BKE_mesh.h
+++ b/source/blender/blenkernel/BKE_mesh.h
@@ -299,7 +299,7 @@ void BKE_mesh_recalc_looptri_with_normals(const struct MLoop *mloop,
struct MLoopTri *mlooptri,
const float (*poly_normals)[3]);
-/* *** mesh_normals.c *** */
+/* *** mesh_normals.cc *** */
void BKE_mesh_calc_normals_mapping_simple(struct Mesh *me);
void BKE_mesh_calc_normals_mapping(struct MVert *mverts,
@@ -494,7 +494,7 @@ void BKE_mesh_calc_normals_split_ex(struct Mesh *mesh,
void BKE_mesh_set_custom_normals(struct Mesh *mesh, float (*r_custom_loopnors)[3]);
void BKE_mesh_set_custom_normals_from_vertices(struct Mesh *mesh, float (*r_custom_vertnors)[3]);
-/* *** mesh_evaluate.c *** */
+/* *** mesh_evaluate.cc *** */
void BKE_mesh_calc_poly_normal(const struct MPoly *mpoly,
const struct MLoop *loopstart,
diff --git a/source/blender/blenkernel/BKE_mesh_types.h b/source/blender/blenkernel/BKE_mesh_types.h
index aed8c44a031..b223d3872ff 100644
--- a/source/blender/blenkernel/BKE_mesh_types.h
+++ b/source/blender/blenkernel/BKE_mesh_types.h
@@ -27,6 +27,7 @@ typedef enum eMeshBatchDirtyMode {
BKE_MESH_BATCH_DIRTY_SELECT,
BKE_MESH_BATCH_DIRTY_SELECT_PAINT,
BKE_MESH_BATCH_DIRTY_SHADING,
+ BKE_MESH_BATCH_DIRTY_DEFORM,
BKE_MESH_BATCH_DIRTY_UVEDIT_ALL,
BKE_MESH_BATCH_DIRTY_UVEDIT_SELECT,
} eMeshBatchDirtyMode;
diff --git a/source/blender/blenkernel/BKE_node.h b/source/blender/blenkernel/BKE_node.h
index 7f4189a3a4a..b1a38ec5700 100644
--- a/source/blender/blenkernel/BKE_node.h
+++ b/source/blender/blenkernel/BKE_node.h
@@ -141,7 +141,10 @@ typedef void *SocketGetCPPValueFunction;
* Defines the appearance and behavior of a socket in the UI.
*/
typedef struct bNodeSocketType {
- char idname[64]; /* identifier name */
+ /* Identifier name */
+ char idname[64];
+ /* Type label */
+ char label[64];
void (*draw)(struct bContext *C,
struct uiLayout *layout,
@@ -412,7 +415,7 @@ typedef struct bNodeTreeType {
void (*node_add_init)(struct bNodeTree *ntree, struct bNode *bnode);
/* Check if the socket type is valid for this tree type. */
- bool (*valid_socket_type)(enum eNodeSocketDatatype socket_type, struct bNodeTreeType *ntreetype);
+ bool (*valid_socket_type)(struct bNodeTreeType *ntreetype, struct bNodeSocketType *socket_type);
/* RNA integration */
ExtensionRNA rna_ext;
@@ -554,8 +557,12 @@ void nodeRegisterSocketType(struct bNodeSocketType *stype);
void nodeUnregisterSocketType(struct bNodeSocketType *stype);
bool nodeSocketIsRegistered(struct bNodeSocket *sock);
struct GHashIterator *nodeSocketTypeGetIterator(void);
+const char *nodeSocketTypeLabel(const bNodeSocketType *stype);
+
+bool nodeIsStaticSocketType(const struct bNodeSocketType *stype);
const char *nodeStaticSocketType(int type, int subtype);
const char *nodeStaticSocketInterfaceType(int type, int subtype);
+const char *nodeStaticSocketLabel(int type, int subtype);
/* helper macros for iterating over node types */
#define NODE_SOCKET_TYPES_BEGIN(stype) \
@@ -605,7 +612,11 @@ struct bNodeSocket *nodeInsertStaticSocket(struct bNodeTree *ntree,
const char *name);
void nodeRemoveSocket(struct bNodeTree *ntree, struct bNode *node, struct bNodeSocket *sock);
void nodeRemoveAllSockets(struct bNodeTree *ntree, struct bNode *node);
-void nodeModifySocketType(
+void nodeModifySocketType(struct bNodeTree *ntree,
+ struct bNode *node,
+ struct bNodeSocket *sock,
+ const char *idname);
+void nodeModifySocketTypeStatic(
struct bNodeTree *ntree, struct bNode *node, struct bNodeSocket *sock, int type, int subtype);
struct bNode *nodeAddNode(const struct bContext *C, struct bNodeTree *ntree, const char *idname);
@@ -1406,7 +1417,7 @@ int ntreeTexExecTree(struct bNodeTree *ntree,
#define GEO_NODE_VOLUME_TO_MESH 1026
#define GEO_NODE_ATTRIBUTE_COMBINE_XYZ 1027
#define GEO_NODE_ATTRIBUTE_SEPARATE_XYZ 1028
-#define GEO_NODE_SUBDIVIDE 1029
+#define GEO_NODE_MESH_SUBDIVIDE 1029
#define GEO_NODE_ATTRIBUTE_REMOVE 1030
#define GEO_NODE_ATTRIBUTE_CONVERT 1031
#define GEO_NODE_MESH_PRIMITIVE_CUBE 1032
@@ -1446,6 +1457,8 @@ int ntreeTexExecTree(struct bNodeTree *ntree,
#define GEO_NODE_CURVE_PRIMITIVE_CIRCLE 1066
#define GEO_NODE_VIEWER 1067
#define GEO_NODE_CURVE_PRIMITIVE_LINE 1068
+#define GEO_NODE_CURVE_ENDPOINTS 1069
+#define GEO_NODE_CURVE_PRIMITIVE_QUADRILATERAL 1070
/** \} */
diff --git a/source/blender/blenkernel/BKE_node_ui_storage.hh b/source/blender/blenkernel/BKE_node_ui_storage.hh
deleted file mode 100644
index 4ec165aad8c..00000000000
--- a/source/blender/blenkernel/BKE_node_ui_storage.hh
+++ /dev/null
@@ -1,133 +0,0 @@
-/*
- * This program is free software; you can redistribute it and/or
- * modify it under the terms of the GNU General Public License
- * as published by the Free Software Foundation; either version 2
- * of the License, or (at your option) any later version.
- *
- * This program is distributed in the hope that it will be useful,
- * but WITHOUT ANY WARRANTY; without even the implied warranty of
- * MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the
- * GNU General Public License for more details.
- *
- * You should have received a copy of the GNU General Public License
- * along with this program; if not, write to the Free Software Foundation,
- * Inc., 51 Franklin Street, Fifth Floor, Boston, MA 02110-1301, USA.
- */
-
-#pragma once
-
-#include <mutex>
-
-#include "BLI_hash.hh"
-#include "BLI_map.hh"
-#include "BLI_session_uuid.h"
-#include "BLI_set.hh"
-
-#include "DNA_ID.h"
-#include "DNA_customdata_types.h"
-#include "DNA_modifier_types.h"
-#include "DNA_session_uuid_types.h"
-
-#include "BKE_attribute.h"
-
-struct ModifierData;
-struct Object;
-struct bNode;
-struct bNodeTree;
-struct bContext;
-
-/**
- * Contains the context necessary to determine when to display settings for a certain node tree
- * that may be used for multiple modifiers and objects. The object name and modifier session UUID
- * are used instead of pointers because they are re-allocated between evaluations.
- *
- * \note This does not yet handle the context of nested node trees.
- */
-class NodeTreeEvaluationContext {
- private:
- std::string object_name_;
- SessionUUID modifier_session_uuid_;
-
- public:
- NodeTreeEvaluationContext(const Object &object, const ModifierData &modifier)
- {
- object_name_ = reinterpret_cast<const ID &>(object).name;
- modifier_session_uuid_ = modifier.session_uuid;
- }
-
- uint64_t hash() const
- {
- return blender::get_default_hash_2(object_name_, modifier_session_uuid_);
- }
-
- friend bool operator==(const NodeTreeEvaluationContext &a, const NodeTreeEvaluationContext &b)
- {
- return a.object_name_ == b.object_name_ &&
- BLI_session_uuid_is_equal(&a.modifier_session_uuid_, &b.modifier_session_uuid_);
- }
-};
-
-enum class NodeWarningType {
- Error,
- Warning,
- Info,
-};
-
-struct NodeWarning {
- NodeWarningType type;
- std::string message;
-};
-
-struct AvailableAttributeInfo {
- std::string name;
- AttributeDomain domain;
- CustomDataType data_type;
-
- uint64_t hash() const
- {
- return blender::get_default_hash(name);
- }
-
- friend bool operator==(const AvailableAttributeInfo &a, const AvailableAttributeInfo &b)
- {
- return a.name == b.name;
- }
-};
-
-struct NodeUIStorage {
- blender::Vector<NodeWarning> warnings;
- blender::Set<AvailableAttributeInfo> attribute_hints;
-};
-
-struct NodeTreeUIStorage {
- std::mutex mutex;
- blender::Map<NodeTreeEvaluationContext, blender::Map<std::string, NodeUIStorage>> context_map;
-
- /**
- * Attribute search uses this to store the fake info for the string typed into a node, in order
- * to pass the info to the execute callback that sets node socket values. This is mutable since
- * we can count on only one attribute search being open at a time, and there is no real data
- * stored here.
- */
- mutable AvailableAttributeInfo dummy_info_for_search;
-};
-
-const NodeUIStorage *BKE_node_tree_ui_storage_get_from_context(const bContext *C,
- const bNodeTree &ntree,
- const bNode &node);
-
-void BKE_nodetree_ui_storage_free_for_context(bNodeTree &ntree,
- const NodeTreeEvaluationContext &context);
-
-void BKE_nodetree_error_message_add(bNodeTree &ntree,
- const NodeTreeEvaluationContext &context,
- const bNode &node,
- const NodeWarningType type,
- std::string message);
-
-void BKE_nodetree_attribute_hint_add(bNodeTree &ntree,
- const NodeTreeEvaluationContext &context,
- const bNode &node,
- const blender::StringRef attribute_name,
- const AttributeDomain domain,
- const CustomDataType data_type);
diff --git a/source/blender/blenkernel/BKE_object.h b/source/blender/blenkernel/BKE_object.h
index cd66f026828..a16822fd7dd 100644
--- a/source/blender/blenkernel/BKE_object.h
+++ b/source/blender/blenkernel/BKE_object.h
@@ -70,10 +70,6 @@ void BKE_object_free_curve_cache(struct Object *ob);
void BKE_object_free_derived_caches(struct Object *ob);
void BKE_object_free_caches(struct Object *object);
-void BKE_object_preview_geometry_set_add(struct Object *ob,
- const uint64_t key,
- struct GeometrySet *geometry_set);
-
void BKE_object_modifier_hook_reset(struct Object *ob, struct HookModifierData *hmd);
void BKE_object_modifier_gpencil_hook_reset(struct Object *ob,
struct HookGpencilModifierData *hmd);
@@ -378,6 +374,10 @@ void BKE_object_runtime_free_data(struct Object *object);
void BKE_object_batch_cache_dirty_tag(struct Object *ob);
void BKE_object_data_batch_cache_dirty_tag(struct ID *object_data);
+void BKE_object_data_eval_batch_cache_dirty_tag(struct Depsgraph *depsgraph,
+ struct ID *object_data);
+void BKE_object_data_eval_batch_cache_deform_tag(struct Depsgraph *depsgraph,
+ struct ID *object_data);
/* this function returns a superset of the scenes selection based on relationships */
diff --git a/source/blender/blenkernel/BKE_pointcache.h b/source/blender/blenkernel/BKE_pointcache.h
index 8731162b720..3f99a0dc793 100644
--- a/source/blender/blenkernel/BKE_pointcache.h
+++ b/source/blender/blenkernel/BKE_pointcache.h
@@ -45,7 +45,7 @@ extern "C" {
#define PTCACHE_RESET_OUTDATED 2
/* #define PTCACHE_RESET_FREE 3 */ /*UNUSED*/
-/* Add the blendfile name after blendcache_ */
+/* Add the blend-file name after `blendcache_`. */
#define PTCACHE_EXT ".bphys"
#define PTCACHE_PATH "blendcache_"
diff --git a/source/blender/blenkernel/BKE_scene.h b/source/blender/blenkernel/BKE_scene.h
index 9792f819bf9..6d58e165ea3 100644
--- a/source/blender/blenkernel/BKE_scene.h
+++ b/source/blender/blenkernel/BKE_scene.h
@@ -124,14 +124,16 @@ bool BKE_scene_camera_switch_update(struct Scene *scene);
const char *BKE_scene_find_marker_name(const struct Scene *scene, int frame);
const char *BKE_scene_find_last_marker_name(const struct Scene *scene, int frame);
-int BKE_scene_frame_snap_by_seconds(struct Scene *scene, double interval_in_seconds, int cfra);
+int BKE_scene_frame_snap_by_seconds(struct Scene *scene, double interval_in_seconds, int frame);
/* checks for cycle, returns 1 if it's all OK */
bool BKE_scene_validate_setscene(struct Main *bmain, struct Scene *sce);
+float BKE_scene_ctime_get(const struct Scene *scene);
+float BKE_scene_frame_to_ctime(const struct Scene *scene, const int frame);
+
float BKE_scene_frame_get(const struct Scene *scene);
-float BKE_scene_frame_to_ctime(const struct Scene *scene, const float frame);
-void BKE_scene_frame_set(struct Scene *scene, double cfra);
+void BKE_scene_frame_set(struct Scene *scene, float frame);
struct TransformOrientationSlot *BKE_scene_orientation_slot_get_from_flag(struct Scene *scene,
int flag);
diff --git a/source/blender/blenkernel/BKE_studiolight.h b/source/blender/blenkernel/BKE_studiolight.h
index 70b8743bcd2..59b1c2b28d9 100644
--- a/source/blender/blenkernel/BKE_studiolight.h
+++ b/source/blender/blenkernel/BKE_studiolight.h
@@ -145,7 +145,7 @@ typedef struct StudioLight {
void BKE_studiolight_init(void);
void BKE_studiolight_free(void);
-void BKE_studiolight_default(SolidLight lights[4], float light_ambient[4]);
+void BKE_studiolight_default(SolidLight lights[4], float light_ambient[3]);
struct StudioLight *BKE_studiolight_find(const char *name, int flag);
struct StudioLight *BKE_studiolight_findindex(int index, int flag);
struct StudioLight *BKE_studiolight_find_default(int flag);
diff --git a/source/blender/blenkernel/BKE_undo_system.h b/source/blender/blenkernel/BKE_undo_system.h
index efac5d9097f..2973a432723 100644
--- a/source/blender/blenkernel/BKE_undo_system.h
+++ b/source/blender/blenkernel/BKE_undo_system.h
@@ -162,6 +162,13 @@ typedef enum UndoTypeFlags {
* \note Callback is still supposed to properly deal with a NULL context pointer.
*/
UNDOTYPE_FLAG_NEED_CONTEXT_FOR_ENCODE = 1 << 0,
+
+ /**
+ * When the active undo step is of this type, it must be read before loading other undo steps.
+ *
+ * This is typically used for undo systems that store both before/after states.
+ */
+ UNDOTYPE_FLAG_DECODE_ACTIVE_STEP = 1 << 1,
} UndoTypeFlags;
/* Expose since we need to perform operations on specific undo types (rarely). */
diff --git a/source/blender/blenkernel/CMakeLists.txt b/source/blender/blenkernel/CMakeLists.txt
index 7a057d8fc1b..2c25b940578 100644
--- a/source/blender/blenkernel/CMakeLists.txt
+++ b/source/blender/blenkernel/CMakeLists.txt
@@ -184,13 +184,13 @@ set(SRC
intern/mesh.c
intern/mesh_boolean_convert.cc
intern/mesh_convert.c
- intern/mesh_evaluate.c
+ intern/mesh_evaluate.cc
intern/mesh_fair.cc
intern/mesh_iterators.c
intern/mesh_mapping.c
intern/mesh_merge.c
intern/mesh_mirror.c
- intern/mesh_normals.c
+ intern/mesh_normals.cc
intern/mesh_remap.c
intern/mesh_remesh_voxel.c
intern/mesh_runtime.c
@@ -215,7 +215,6 @@ set(SRC
intern/multires_versioning.c
intern/nla.c
intern/node.cc
- intern/node_ui_storage.cc
intern/object.c
intern/object_deform.c
intern/object_dupli.cc
@@ -331,7 +330,6 @@ set(SRC
BKE_customdata_file.h
BKE_data_transfer.h
BKE_deform.h
- BKE_spline.hh
BKE_displist.h
BKE_displist_tangent.h
BKE_duplilist.h
@@ -399,7 +397,6 @@ set(SRC
BKE_multires.h
BKE_nla.h
BKE_node.h
- BKE_node_ui_storage.hh
BKE_object.h
BKE_object_deform.h
BKE_object_facemap.h
@@ -423,6 +420,7 @@ set(SRC
BKE_softbody.h
BKE_sound.h
BKE_speaker.h
+ BKE_spline.hh
BKE_studiolight.h
BKE_subdiv.h
BKE_subdiv_ccg.h
@@ -767,6 +765,7 @@ add_dependencies(bf_blenkernel bf_dna)
if(WITH_GTESTS)
set(TEST_SRC
+ intern/action_test.cc
intern/armature_test.cc
intern/cryptomatte_test.cc
intern/fcurve_test.cc
diff --git a/source/blender/blenkernel/intern/DerivedMesh.cc b/source/blender/blenkernel/intern/DerivedMesh.cc
index 933cddfdf1b..ba8cf8debe9 100644
--- a/source/blender/blenkernel/intern/DerivedMesh.cc
+++ b/source/blender/blenkernel/intern/DerivedMesh.cc
@@ -1976,7 +1976,7 @@ static void editbmesh_build_data(struct Depsgraph *depsgraph,
BKE_sculpt_update_object_before_eval(obedit);
}
- BKE_editmesh_free_derivedmesh(em);
+ BKE_editmesh_free_derived_caches(em);
Mesh *me_cage;
Mesh *me_final;
diff --git a/source/blender/blenkernel/intern/action.c b/source/blender/blenkernel/intern/action.c
index 13ca5ecf23c..d55f023d209 100644
--- a/source/blender/blenkernel/intern/action.c
+++ b/source/blender/blenkernel/intern/action.c
@@ -497,9 +497,8 @@ void action_groups_add_channel(bAction *act, bActionGroup *agrp, FCurve *fcurve)
}
/* Reconstruct group channel pointers.
- * Assumes that the channels are still in the proper order, i.e. that channels of the same group
- * are adjacent in the act->channels list. It also assumes that the groups
- * referred to by the FCurves are already in act->groups.
+ * Assumes that the groups referred to by the FCurves are already in act->groups.
+ * Reorders the main channel list to match group order.
*/
void BKE_action_groups_reconstruct(bAction *act)
{
@@ -514,23 +513,30 @@ void BKE_action_groups_reconstruct(bAction *act)
BLI_listbase_clear(&group->channels);
}
- bActionGroup *grp;
- bActionGroup *last_grp = NULL;
- LISTBASE_FOREACH (FCurve *, fcurve, &act->curves) {
- if (fcurve->grp == NULL) {
- continue;
- }
+ /* Sort the channels into the group lists, destroying the act->curves list. */
+ ListBase ungrouped = {NULL, NULL};
- grp = fcurve->grp;
- if (last_grp != grp) {
- /* If this is the first time we see this group, this must be the first channel. */
- grp->channels.first = fcurve;
+ LISTBASE_FOREACH_MUTABLE (FCurve *, fcurve, &act->curves) {
+ if (fcurve->grp) {
+ BLI_assert(BLI_findindex(&act->groups, fcurve->grp) >= 0);
+
+ BLI_addtail(&fcurve->grp->channels, fcurve);
+ }
+ else {
+ BLI_addtail(&ungrouped, fcurve);
}
+ }
+
+ /* Recombine into the main list. */
+ BLI_listbase_clear(&act->curves);
- /* This is the last channel, until it's overwritten by a later iteration. */
- grp->channels.last = fcurve;
- last_grp = grp;
+ LISTBASE_FOREACH (bActionGroup *, group, &act->groups) {
+ /* Copy the list header to preserve the pointers in the group. */
+ ListBase tmp = group->channels;
+ BLI_movelisttolist(&act->curves, &tmp);
}
+
+ BLI_movelisttolist(&act->curves, &ungrouped);
}
/* Remove the given channel from all groups */
diff --git a/source/blender/blenkernel/intern/action_test.cc b/source/blender/blenkernel/intern/action_test.cc
new file mode 100644
index 00000000000..c02eca966ad
--- /dev/null
+++ b/source/blender/blenkernel/intern/action_test.cc
@@ -0,0 +1,144 @@
+/*
+ * This program is free software; you can redistribute it and/or
+ * modify it under the terms of the GNU General Public License
+ * as published by the Free Software Foundation; either version 2
+ * of the License, or (at your option) any later version.
+ *
+ * This program is distributed in the hope that it will be useful,
+ * but WITHOUT ANY WARRANTY; without even the implied warranty of
+ * MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the
+ * GNU General Public License for more details.
+ *
+ * You should have received a copy of the GNU General Public License
+ * along with this program; if not, write to the Free Software Foundation,
+ * Inc., 51 Franklin Street, Fifth Floor, Boston, MA 02110-1301, USA.
+ *
+ * The Original Code is Copyright (C) 2021 Blender Foundation
+ * All rights reserved.
+ */
+
+#include "BKE_action.h"
+
+#include "DNA_action_types.h"
+#include "DNA_anim_types.h"
+
+#include "BLI_listbase.h"
+
+#include "testing/testing.h"
+
+namespace blender::bke::tests {
+
+TEST(action_groups, ReconstructGroupsWithReordering)
+{
+ /* Construct an Action with three groups. */
+ bAction action = {{nullptr}};
+ FCurve groupAcurve1 = {nullptr};
+ FCurve groupAcurve2 = {nullptr};
+ FCurve groupBcurve1 = {nullptr};
+ FCurve groupBcurve2 = {nullptr};
+ FCurve groupBcurve3 = {nullptr};
+ /* Group C has no curves intentionally. */
+ FCurve groupDcurve1 = {nullptr};
+ FCurve groupDcurve2 = {nullptr};
+
+ groupAcurve1.rna_path = (char *)"groupAcurve1";
+ groupAcurve2.rna_path = (char *)"groupAcurve2";
+ groupBcurve1.rna_path = (char *)"groupBcurve1";
+ groupBcurve2.rna_path = (char *)"groupBcurve2";
+ groupDcurve1.rna_path = (char *)"groupDcurve1";
+ groupBcurve3.rna_path = (char *)"groupBcurve3";
+ groupDcurve2.rna_path = (char *)"groupDcurve2";
+
+ BLI_addtail(&action.curves, &groupAcurve1);
+ BLI_addtail(&action.curves, &groupAcurve2);
+ BLI_addtail(&action.curves, &groupBcurve1);
+ BLI_addtail(&action.curves, &groupBcurve2);
+ BLI_addtail(&action.curves, &groupDcurve1);
+ BLI_addtail(&action.curves, &groupBcurve3); /* <-- The error that should be corrected. */
+ BLI_addtail(&action.curves, &groupDcurve2);
+
+ /* Introduce another error type, by changing some `prev` pointers. */
+ groupBcurve1.prev = nullptr;
+ groupBcurve3.prev = &groupBcurve2;
+ groupDcurve1.prev = &groupBcurve3;
+
+ bActionGroup groupA = {nullptr};
+ bActionGroup groupB = {nullptr};
+ bActionGroup groupC = {nullptr};
+ bActionGroup groupD = {nullptr};
+ strcpy(groupA.name, "groupA");
+ strcpy(groupB.name, "groupB");
+ strcpy(groupC.name, "groupC");
+ strcpy(groupD.name, "groupD");
+
+ BLI_addtail(&action.groups, &groupA);
+ BLI_addtail(&action.groups, &groupB);
+ BLI_addtail(&action.groups, &groupC);
+ BLI_addtail(&action.groups, &groupD);
+
+ groupAcurve1.grp = &groupA;
+ groupAcurve2.grp = &groupA;
+ groupBcurve1.grp = &groupB;
+ groupBcurve2.grp = &groupB;
+ groupBcurve3.grp = &groupB;
+ groupDcurve1.grp = &groupD;
+ groupDcurve2.grp = &groupD;
+
+ groupA.channels.first = &groupAcurve1;
+ groupA.channels.last = &groupAcurve2;
+ groupB.channels.first = &groupBcurve1;
+ groupB.channels.last = &groupBcurve3; /* The last channel in group B, after group C curve 1. */
+ groupD.channels.first = &groupDcurve1;
+ groupD.channels.last = &groupDcurve2;
+
+ EXPECT_EQ(groupA.channels.first, &groupAcurve1);
+ EXPECT_EQ(groupA.channels.last, &groupAcurve2);
+ EXPECT_EQ(groupB.channels.first, &groupBcurve1);
+ EXPECT_EQ(groupB.channels.last, &groupBcurve3);
+ EXPECT_EQ(groupC.channels.first, nullptr);
+ EXPECT_EQ(groupC.channels.last, nullptr);
+ EXPECT_EQ(groupD.channels.first, &groupDcurve1);
+ EXPECT_EQ(groupD.channels.last, &groupDcurve2);
+
+ BKE_action_groups_reconstruct(&action);
+
+ EXPECT_EQ(action.curves.first, &groupAcurve1);
+ EXPECT_EQ(action.curves.last, &groupDcurve2);
+
+ EXPECT_EQ(groupA.prev, nullptr);
+ EXPECT_EQ(groupB.prev, &groupA);
+ EXPECT_EQ(groupC.prev, &groupB);
+ EXPECT_EQ(groupD.prev, &groupC);
+
+ EXPECT_EQ(groupA.next, &groupB);
+ EXPECT_EQ(groupB.next, &groupC);
+ EXPECT_EQ(groupC.next, &groupD);
+ EXPECT_EQ(groupD.next, nullptr);
+
+ EXPECT_EQ(groupA.channels.first, &groupAcurve1);
+ EXPECT_EQ(groupA.channels.last, &groupAcurve2);
+ EXPECT_EQ(groupB.channels.first, &groupBcurve1);
+ EXPECT_EQ(groupB.channels.last, &groupBcurve3);
+ EXPECT_EQ(groupC.channels.first, nullptr);
+ EXPECT_EQ(groupC.channels.last, nullptr);
+ EXPECT_EQ(groupD.channels.first, &groupDcurve1);
+ EXPECT_EQ(groupD.channels.last, &groupDcurve2);
+
+ EXPECT_EQ(groupAcurve1.prev, nullptr);
+ EXPECT_EQ(groupAcurve2.prev, &groupAcurve1);
+ EXPECT_EQ(groupBcurve1.prev, &groupAcurve2);
+ EXPECT_EQ(groupBcurve2.prev, &groupBcurve1);
+ EXPECT_EQ(groupBcurve3.prev, &groupBcurve2);
+ EXPECT_EQ(groupDcurve1.prev, &groupBcurve3);
+ EXPECT_EQ(groupDcurve2.prev, &groupDcurve1);
+
+ EXPECT_EQ(groupAcurve1.next, &groupAcurve2);
+ EXPECT_EQ(groupAcurve2.next, &groupBcurve1);
+ EXPECT_EQ(groupBcurve1.next, &groupBcurve2);
+ EXPECT_EQ(groupBcurve2.next, &groupBcurve3);
+ EXPECT_EQ(groupBcurve3.next, &groupDcurve1);
+ EXPECT_EQ(groupDcurve1.next, &groupDcurve2);
+ EXPECT_EQ(groupDcurve2.next, nullptr);
+}
+
+} // namespace blender::bke::tests
diff --git a/source/blender/blenkernel/intern/anim_data.c b/source/blender/blenkernel/intern/anim_data.c
index 7e5313f0e4a..7e4ab754500 100644
--- a/source/blender/blenkernel/intern/anim_data.c
+++ b/source/blender/blenkernel/intern/anim_data.c
@@ -89,16 +89,16 @@ bool id_can_have_animdata(const ID *id)
return id_type_can_have_animdata(GS(id->name));
}
-/* Get AnimData from the given ID-block. In order for this to work, we assume that
- * the AnimData pointer is stored immediately after the given ID-block in the struct,
- * as per IdAdtTemplate.
+/**
+ * Get #AnimData from the given ID-block.
*/
AnimData *BKE_animdata_from_id(ID *id)
{
- /* only some ID-blocks have this info for now, so we cast the
- * types that do to be of type IdAdtTemplate, and extract the
- * AnimData that way
- */
+ /* In order for this to work, we assume that the #AnimData pointer is stored
+ * immediately after the given ID-block in the struct, as per IdAdtTemplate. */
+
+ /* Only some ID-blocks have this info for now, so we cast the types that do
+ * to be of type IdAdtTemplate, and add the AnimData to it using the template. */
if (id_can_have_animdata(id)) {
IdAdtTemplate *iat = (IdAdtTemplate *)id;
return iat->adt;
@@ -106,16 +106,16 @@ AnimData *BKE_animdata_from_id(ID *id)
return NULL;
}
-/* Add AnimData to the given ID-block. In order for this to work, we assume that
- * the AnimData pointer is stored immediately after the given ID-block in the struct,
- * as per IdAdtTemplate. Also note that
+/**
+ * Ensure #AnimData exists in the given ID-block (when supported).
*/
-AnimData *BKE_animdata_add_id(ID *id)
+AnimData *BKE_animdata_ensure_id(ID *id)
{
- /* Only some ID-blocks have this info for now, so we cast the
- * types that do to be of type IdAdtTemplate, and add the AnimData
- * to it using the template
- */
+ /* In order for this to work, we assume that the #AnimData pointer is stored
+ * immediately after the given ID-block in the struct, as per IdAdtTemplate. */
+
+ /* Only some ID-blocks have this info for now, so we cast the types that do
+ * to be of type IdAdtTemplate, and add the AnimData to it using the template. */
if (id_can_have_animdata(id)) {
IdAdtTemplate *iat = (IdAdtTemplate *)id;
@@ -444,7 +444,7 @@ void BKE_animdata_merge_copy(
return;
}
- // TODO: we must unset all "tweakmode" flags
+ /* TODO: we must unset all "tweak-mode" flags. */
if ((src->flag & ADT_NLA_EDIT_ON) || (dst->flag & ADT_NLA_EDIT_ON)) {
CLOG_ERROR(
&LOG,
@@ -667,7 +667,7 @@ void BKE_animdata_transfer_by_basepath(Main *bmain, ID *srcID, ID *dstID, ListBa
/* get animdata from src, and create for destination (if needed) */
srcAdt = BKE_animdata_from_id(srcID);
- dstAdt = BKE_animdata_add_id(dstID);
+ dstAdt = BKE_animdata_ensure_id(dstID);
if (ELEM(NULL, srcAdt, dstAdt)) {
if (G.debug & G_DEBUG) {
@@ -1590,10 +1590,10 @@ void BKE_animdata_blend_read_data(BlendDataReader *reader, AnimData *adt)
/* relink active track/strip - even though strictly speaking this should only be used
* if we're in 'tweaking mode', we need to be able to have this loaded back for
- * undo, but also since users may not exit tweakmode before saving (T24535)
+ * undo, but also since users may not exit tweak-mode before saving (T24535).
*/
/* TODO: it's not really nice that anyone should be able to save the file in this
- * state, but it's going to be too hard to enforce this single case... */
+ * state, but it's going to be too hard to enforce this single case. */
BLO_read_data_address(reader, &adt->act_track);
BLO_read_data_address(reader, &adt->actstrip);
}
diff --git a/source/blender/blenkernel/intern/appdir.c b/source/blender/blenkernel/intern/appdir.c
index 579f671e2b0..ebff6015df1 100644
--- a/source/blender/blenkernel/intern/appdir.c
+++ b/source/blender/blenkernel/intern/appdir.c
@@ -191,8 +191,7 @@ bool BKE_appdir_folder_documents(char *dir)
{
dir[0] = '\0';
- const char *documents_path = (const char *)GHOST_getUserSpecialDir(
- GHOST_kUserSpecialDirDocuments);
+ const char *documents_path = GHOST_getUserSpecialDir(GHOST_kUserSpecialDirDocuments);
/* Usual case: Ghost gave us the documents path. We're done here. */
if (documents_path && BLI_is_dir(documents_path)) {
@@ -462,7 +461,7 @@ static bool get_path_user_ex(char *targetpath,
}
user_path[0] = '\0';
- user_base_path = (const char *)GHOST_getUserDir(version, blender_version_decimal(version));
+ user_base_path = GHOST_getUserDir(version, blender_version_decimal(version));
if (user_base_path) {
BLI_strncpy(user_path, user_base_path, FILE_MAX);
}
@@ -522,7 +521,7 @@ static bool get_path_system_ex(char *targetpath,
}
system_path[0] = '\0';
- system_base_path = (const char *)GHOST_getSystemDir(version, blender_version_decimal(version));
+ system_base_path = GHOST_getSystemDir(version, blender_version_decimal(version));
if (system_base_path) {
BLI_strncpy(system_path, system_base_path, FILE_MAX);
}
diff --git a/source/blender/blenkernel/intern/armature.c b/source/blender/blenkernel/intern/armature.c
index 22d6cfba893..b8ed519e8d1 100644
--- a/source/blender/blenkernel/intern/armature.c
+++ b/source/blender/blenkernel/intern/armature.c
@@ -2843,7 +2843,7 @@ void BKE_pose_where_is(struct Depsgraph *depsgraph, Scene *scene, Object *ob)
* hopefully this is OK. */
BKE_pose_ensure(NULL, ob, arm, true);
- ctime = BKE_scene_frame_get(scene); /* not accurate... */
+ ctime = BKE_scene_ctime_get(scene); /* not accurate... */
/* In edit-mode or rest-position we read the data from the bones. */
if (arm->edbo || (arm->flag & ARM_RESTPOS)) {
diff --git a/source/blender/blenkernel/intern/armature_deform.c b/source/blender/blenkernel/intern/armature_deform.c
index 2552b5eefea..5e9259f05bb 100644
--- a/source/blender/blenkernel/intern/armature_deform.c
+++ b/source/blender/blenkernel/intern/armature_deform.c
@@ -47,6 +47,7 @@
#include "BKE_action.h"
#include "BKE_armature.h"
+#include "BKE_customdata.h"
#include "BKE_deform.h"
#include "BKE_editmesh.h"
#include "BKE_lattice.h"
diff --git a/source/blender/blenkernel/intern/armature_update.c b/source/blender/blenkernel/intern/armature_update.c
index 0f8956a1a91..35ae2d2dbef 100644
--- a/source/blender/blenkernel/intern/armature_update.c
+++ b/source/blender/blenkernel/intern/armature_update.c
@@ -562,7 +562,7 @@ static void splineik_evaluate_bone(
* spline dictates, while still maintaining roll control from the existing bone animation. */
mul_m3_m3m3(pose_mat, dmat, rmat);
- /* Attempt to reduce shearing, though I doubt this'll really help too much now... */
+ /* Attempt to reduce shearing, though I doubt this will really help too much now. */
normalize_m3(pose_mat);
mul_m3_m3m3(base_pose_mat, dmat, base_pose_mat);
@@ -828,7 +828,7 @@ void BKE_pose_eval_init_ik(struct Depsgraph *depsgraph, Scene *scene, Object *ob
{
DEG_debug_print_eval(depsgraph, __func__, object->id.name, object);
BLI_assert(object->type == OB_ARMATURE);
- const float ctime = BKE_scene_frame_get(scene); /* not accurate... */
+ const float ctime = BKE_scene_ctime_get(scene); /* not accurate... */
bArmature *armature = (bArmature *)object->data;
if (armature->flag & ARM_RESTPOS) {
return;
@@ -869,7 +869,7 @@ void BKE_pose_eval_bone(struct Depsgraph *depsgraph, Scene *scene, Object *objec
else {
if ((pchan->flag & POSE_DONE) == 0) {
/* TODO(sergey): Use time source node for time. */
- float ctime = BKE_scene_frame_get(scene); /* not accurate... */
+ float ctime = BKE_scene_ctime_get(scene); /* not accurate... */
BKE_pose_where_is_bone(depsgraph, scene, object, pchan, ctime, 1);
}
}
@@ -897,7 +897,7 @@ void BKE_pose_constraints_evaluate(struct Depsgraph *depsgraph,
}
else {
if ((pchan->flag & POSE_DONE) == 0) {
- float ctime = BKE_scene_frame_get(scene); /* not accurate... */
+ float ctime = BKE_scene_ctime_get(scene); /* not accurate... */
BKE_pose_where_is_bone(depsgraph, scene, object, pchan, ctime, 1);
}
}
@@ -981,7 +981,7 @@ void BKE_pose_iktree_evaluate(struct Depsgraph *depsgraph,
DEG_debug_print_eval_subdata(
depsgraph, __func__, object->id.name, object, "rootchan", rootchan->name, rootchan);
BLI_assert(object->type == OB_ARMATURE);
- const float ctime = BKE_scene_frame_get(scene); /* not accurate... */
+ const float ctime = BKE_scene_ctime_get(scene); /* not accurate... */
if (armature->flag & ARM_RESTPOS) {
return;
}
@@ -1002,7 +1002,7 @@ void BKE_pose_splineik_evaluate(struct Depsgraph *depsgraph,
DEG_debug_print_eval_subdata(
depsgraph, __func__, object->id.name, object, "rootchan", rootchan->name, rootchan);
BLI_assert(object->type == OB_ARMATURE);
- const float ctime = BKE_scene_frame_get(scene); /* not accurate... */
+ const float ctime = BKE_scene_ctime_get(scene); /* not accurate... */
if (armature->flag & ARM_RESTPOS) {
return;
}
@@ -1031,7 +1031,7 @@ void BKE_pose_eval_cleanup(struct Depsgraph *depsgraph, Scene *scene, Object *ob
bPose *pose = object->pose;
BLI_assert(pose != NULL);
UNUSED_VARS_NDEBUG(pose);
- const float ctime = BKE_scene_frame_get(scene); /* not accurate... */
+ const float ctime = BKE_scene_ctime_get(scene); /* not accurate... */
DEG_debug_print_eval(depsgraph, __func__, object->id.name, object);
BLI_assert(object->type == OB_ARMATURE);
/* Release the IK tree. */
diff --git a/source/blender/blenkernel/intern/blendfile.c b/source/blender/blenkernel/intern/blendfile.c
index f31d8f5ade7..912cc66920e 100644
--- a/source/blender/blenkernel/intern/blendfile.c
+++ b/source/blender/blenkernel/intern/blendfile.c
@@ -128,7 +128,7 @@ static void setup_app_userdef(BlendFileData *bfd)
}
/**
- * Context matching, handle no-ui case
+ * Context matching, handle no-UI case.
*
* \note this is called on Undo so any slow conversion functions here
* should be avoided or check (mode != LOAD_UNDO).
diff --git a/source/blender/blenkernel/intern/bvhutils.cc b/source/blender/blenkernel/intern/bvhutils.cc
index 0284b20d98e..164f921c7ac 100644
--- a/source/blender/blenkernel/intern/bvhutils.cc
+++ b/source/blender/blenkernel/intern/bvhutils.cc
@@ -1290,9 +1290,9 @@ BVHTree *bvhtree_from_editmesh_looptri(
}
/**
- * Builds a bvh tree where nodes are the looptri faces of the given dm
+ * Builds a BVH-tree where nodes are the looptri faces of the given mesh.
*
- * \note for editmesh this is currently a duplicate of bvhtree_from_mesh_faces_ex
+ * \note for edit-mesh this is currently a duplicate of #bvhtree_from_mesh_faces_ex
*/
BVHTree *bvhtree_from_mesh_looptri_ex(BVHTreeFromMesh *data,
const struct MVert *vert,
diff --git a/source/blender/blenkernel/intern/cachefile.c b/source/blender/blenkernel/intern/cachefile.c
index 30e9ae39b67..eaba5d33a20 100644
--- a/source/blender/blenkernel/intern/cachefile.c
+++ b/source/blender/blenkernel/intern/cachefile.c
@@ -314,7 +314,7 @@ bool BKE_cachefile_filepath_get(const Main *bmain,
if (cache_file->is_sequence && BLI_path_frame_get(r_filepath, &fframe, &frame_len)) {
Scene *scene = DEG_get_evaluated_scene(depsgraph);
- const float ctime = BKE_scene_frame_get(scene);
+ const float ctime = BKE_scene_ctime_get(scene);
const float fps = (((double)scene->r.frs_sec) / (double)scene->r.frs_sec_base);
const float frame = BKE_cachefile_time_offset(cache_file, ctime, fps);
diff --git a/source/blender/blenkernel/intern/cloth.c b/source/blender/blenkernel/intern/cloth.c
index 2bca3f5da76..8678a659c0a 100644
--- a/source/blender/blenkernel/intern/cloth.c
+++ b/source/blender/blenkernel/intern/cloth.c
@@ -597,7 +597,7 @@ static void cloth_to_object(Object *ob, ClothModifierData *clmd, float (*vertexC
Cloth *cloth = clmd->clothObject;
if (clmd->clothObject) {
- /* inverse matrix is not uptodate... */
+ /* Inverse matrix is not up to date. */
invert_m4_m4(ob->imat, ob->obmat);
for (i = 0; i < cloth->mvert_num; i++) {
diff --git a/source/blender/blenkernel/intern/collection.c b/source/blender/blenkernel/intern/collection.c
index 39698bde622..cf32bc15962 100644
--- a/source/blender/blenkernel/intern/collection.c
+++ b/source/blender/blenkernel/intern/collection.c
@@ -888,7 +888,7 @@ Collection *BKE_collection_master_add()
{
/* Not an actual datablock, but owned by scene. */
Collection *master_collection = BKE_libblock_alloc(
- NULL, ID_GR, "Master Collection", LIB_ID_CREATE_NO_MAIN);
+ NULL, ID_GR, BKE_SCENE_COLLECTION_NAME, LIB_ID_CREATE_NO_MAIN);
master_collection->id.flag |= LIB_EMBEDDED_DATA;
master_collection->flag |= COLLECTION_IS_MASTER;
master_collection->color_tag = COLLECTION_COLOR_NONE;
diff --git a/source/blender/blenkernel/intern/crazyspace.c b/source/blender/blenkernel/intern/crazyspace.c
index 4e1ec9ba35e..26894495777 100644
--- a/source/blender/blenkernel/intern/crazyspace.c
+++ b/source/blender/blenkernel/intern/crazyspace.c
@@ -398,8 +398,7 @@ int BKE_sculpt_get_first_deform_matrices(struct Depsgraph *depsgraph,
if (crazyspace_modifier_supports_deform_matrices(md)) {
const ModifierTypeInfo *mti = BKE_modifier_get_info(md->type);
if (defmats == NULL) {
- /* NOTE: Evaluated object si re-set to its original undeformed
- * state. */
+ /* NOTE: Evaluated object is re-set to its original un-deformed state. */
Mesh *me = object_eval.data;
me_eval = BKE_mesh_copy_for_eval(me, true);
crazyspace_init_verts_and_matrices(me_eval, &defmats, &deformedVerts);
diff --git a/source/blender/blenkernel/intern/dynamicpaint.c b/source/blender/blenkernel/intern/dynamicpaint.c
index 8dac20f6fe9..52996e3bcc7 100644
--- a/source/blender/blenkernel/intern/dynamicpaint.c
+++ b/source/blender/blenkernel/intern/dynamicpaint.c
@@ -248,7 +248,7 @@ typedef struct PaintAdjData {
int *n_target;
/** Index to start reading n_target for each point. */
int *n_index;
- /** Num of neighs for each point. */
+ /** Number of neighbors for each point. */
int *n_num;
/** Vertex adjacency flags. */
int *flags;
@@ -3818,7 +3818,7 @@ static void dynamicPaint_brushMeshCalculateVelocity(Depsgraph *depsgraph,
ob,
true,
SUBFRAME_RECURSION,
- BKE_scene_frame_get(scene),
+ BKE_scene_ctime_get(scene),
eModifierType_DynamicPaint);
mesh_p = BKE_mesh_copy_for_eval(dynamicPaint_brush_mesh_get(brush), false);
numOfVerts_p = mesh_p->totvert;
@@ -3834,7 +3834,7 @@ static void dynamicPaint_brushMeshCalculateVelocity(Depsgraph *depsgraph,
ob,
true,
SUBFRAME_RECURSION,
- BKE_scene_frame_get(scene),
+ BKE_scene_ctime_get(scene),
eModifierType_DynamicPaint);
mesh_c = dynamicPaint_brush_mesh_get(brush);
numOfVerts_c = mesh_c->totvert;
@@ -3894,7 +3894,7 @@ static void dynamicPaint_brushObjectCalculateVelocity(
ob,
false,
SUBFRAME_RECURSION,
- BKE_scene_frame_get(scene),
+ BKE_scene_ctime_get(scene),
eModifierType_DynamicPaint);
copy_m4_m4(prev_obmat, ob->obmat);
@@ -3906,7 +3906,7 @@ static void dynamicPaint_brushObjectCalculateVelocity(
ob,
false,
SUBFRAME_RECURSION,
- BKE_scene_frame_get(scene),
+ BKE_scene_ctime_get(scene),
eModifierType_DynamicPaint);
/* calculate speed */
@@ -6271,7 +6271,7 @@ static int dynamicPaint_doStep(Depsgraph *depsgraph,
brushObj,
true,
SUBFRAME_RECURSION,
- BKE_scene_frame_get(scene),
+ BKE_scene_ctime_get(scene),
eModifierType_DynamicPaint);
}
@@ -6312,7 +6312,7 @@ static int dynamicPaint_doStep(Depsgraph *depsgraph,
brushObj,
true,
SUBFRAME_RECURSION,
- BKE_scene_frame_get(scene),
+ BKE_scene_ctime_get(scene),
eModifierType_DynamicPaint);
}
diff --git a/source/blender/blenkernel/intern/editmesh.c b/source/blender/blenkernel/intern/editmesh.c
index 2eb6b488da2..9cae74e4e9a 100644
--- a/source/blender/blenkernel/intern/editmesh.c
+++ b/source/blender/blenkernel/intern/editmesh.c
@@ -39,15 +39,14 @@
#include "BKE_mesh_wrapper.h"
#include "BKE_object.h"
-BMEditMesh *BKE_editmesh_create(BMesh *bm, const bool do_tessellate)
+/**
+ * \note The caller is responsible for ensuring triangulation data,
+ * typically by calling #BKE_editmesh_looptri_calc.
+ */
+BMEditMesh *BKE_editmesh_create(BMesh *bm)
{
BMEditMesh *em = MEM_callocN(sizeof(BMEditMesh), __func__);
-
em->bm = bm;
- if (do_tessellate) {
- BKE_editmesh_looptri_calc(em);
- }
-
return em;
}
@@ -209,7 +208,7 @@ void BKE_editmesh_looptri_and_normals_calc_with_partial(BMEditMesh *em,
});
}
-void BKE_editmesh_free_derivedmesh(BMEditMesh *em)
+void BKE_editmesh_free_derived_caches(BMEditMesh *em)
{
if (em->mesh_eval_cage) {
BKE_id_free(NULL, em->mesh_eval_cage);
@@ -223,9 +222,9 @@ void BKE_editmesh_free_derivedmesh(BMEditMesh *em)
}
/* Does not free the #BMEditMesh struct itself. */
-void BKE_editmesh_free(BMEditMesh *em)
+void BKE_editmesh_free_data(BMEditMesh *em)
{
- BKE_editmesh_free_derivedmesh(em);
+ BKE_editmesh_free_derived_caches(em);
if (em->looptris) {
MEM_freeN(em->looptris);
diff --git a/source/blender/blenkernel/intern/editmesh_tangent.c b/source/blender/blenkernel/intern/editmesh_tangent.c
index e5e639fa3f1..da4ea742656 100644
--- a/source/blender/blenkernel/intern/editmesh_tangent.c
+++ b/source/blender/blenkernel/intern/editmesh_tangent.c
@@ -25,6 +25,7 @@
#include "DNA_defs.h"
#include "DNA_meshdata_types.h"
+#include "BKE_customdata.h"
#include "BKE_editmesh.h"
#include "BKE_editmesh_tangent.h"
#include "BKE_mesh.h"
diff --git a/source/blender/blenkernel/intern/fluid.c b/source/blender/blenkernel/intern/fluid.c
index 947417af55d..2b48683a3a8 100644
--- a/source/blender/blenkernel/intern/fluid.c
+++ b/source/blender/blenkernel/intern/fluid.c
@@ -1283,10 +1283,10 @@ static void compute_obstaclesemission(Scene *scene,
# endif
/* Update frame time, this is considering current subframe fraction
* BLI_mutex_lock() called in manta_step(), so safe to update subframe here
- * TODO(sebbas): Using BKE_scene_frame_get(scene) instead of new DEG_get_ctime(depsgraph)
+ * TODO(sebbas): Using BKE_scene_ctime_get(scene) instead of new DEG_get_ctime(depsgraph)
* as subframes don't work with the latter yet. */
BKE_object_modifier_update_subframe(
- depsgraph, scene, effecobj, true, 5, BKE_scene_frame_get(scene), eModifierType_Fluid);
+ depsgraph, scene, effecobj, true, 5, BKE_scene_ctime_get(scene), eModifierType_Fluid);
if (subframes) {
obstacles_from_mesh(effecobj, fds, fes, &bb_temp, subframe_dt);
@@ -1616,7 +1616,7 @@ static void emit_from_particles(Object *flow_ob,
}
/* `DEG_get_ctime(depsgraph)` does not give sub-frame time. */
- state.time = BKE_scene_frame_get(scene);
+ state.time = BKE_scene_ctime_get(scene);
if (psys_get_particle_state(&sim, p, &state, 0) == 0) {
continue;
@@ -2820,10 +2820,10 @@ static void compute_flowsemission(Scene *scene,
# endif
/* Update frame time, this is considering current subframe fraction
* BLI_mutex_lock() called in manta_step(), so safe to update subframe here
- * TODO(sebbas): Using BKE_scene_frame_get(scene) instead of new DEG_get_ctime(depsgraph)
+ * TODO(sebbas): Using BKE_scene_ctime_get(scene) instead of new DEG_get_ctime(depsgraph)
* as subframes don't work with the latter yet. */
BKE_object_modifier_update_subframe(
- depsgraph, scene, flowobj, true, 5, BKE_scene_frame_get(scene), eModifierType_Fluid);
+ depsgraph, scene, flowobj, true, 5, BKE_scene_ctime_get(scene), eModifierType_Fluid);
/* Emission from particles. */
if (ffs->source == FLUID_FLOW_SOURCE_PARTICLES) {
diff --git a/source/blender/blenkernel/intern/gpencil.c b/source/blender/blenkernel/intern/gpencil.c
index 1a880b0c427..529096b8523 100644
--- a/source/blender/blenkernel/intern/gpencil.c
+++ b/source/blender/blenkernel/intern/gpencil.c
@@ -2703,19 +2703,57 @@ static bool gpencil_is_layer_mask(ViewLayer *view_layer, bGPdata *gpd, bGPDlayer
}
/* -------------------------------------------------------------------- */
-/** \name Iterators
+/** \name Iterator
*
- * Iterate over all visible stroke of all visible layers inside a gpObject.
- * Also take into account onion-skinning.
+ * Iterate over all visible stroke of all visible layers inside a grease pencil datablock.
* \{ */
-void BKE_gpencil_visible_stroke_iter(ViewLayer *view_layer,
- Object *ob,
+void BKE_gpencil_visible_stroke_iter(bGPdata *gpd,
gpIterCb layer_cb,
gpIterCb stroke_cb,
- void *thunk,
- bool do_onion,
- int cfra)
+ void *thunk)
+{
+ LISTBASE_FOREACH (bGPDlayer *, gpl, &gpd->layers) {
+
+ if (gpl->flag & GP_LAYER_HIDE) {
+ continue;
+ }
+
+ /* If scale to 0 the layer must be invisible. */
+ if (is_zero_v3(gpl->scale)) {
+ continue;
+ }
+
+ bGPDframe *act_gpf = gpl->actframe;
+ if (layer_cb) {
+ layer_cb(gpl, act_gpf, NULL, thunk);
+ }
+
+ if (act_gpf) {
+ LISTBASE_FOREACH (bGPDstroke *, gps, &act_gpf->strokes) {
+ if (gps->totpoints == 0) {
+ continue;
+ }
+ stroke_cb(gpl, act_gpf, gps, thunk);
+ }
+ }
+ }
+}
+
+/* -------------------------------------------------------------------- */
+/** \name Advanced Iterator
+ *
+ * Iterate over all visible stroke of all visible layers inside a gpObject.
+ * Also take into account onion-skinning.
+ * \{ */
+
+void BKE_gpencil_visible_stroke_advanced_iter(ViewLayer *view_layer,
+ Object *ob,
+ gpIterCb layer_cb,
+ gpIterCb stroke_cb,
+ void *thunk,
+ bool do_onion,
+ int cfra)
{
bGPdata *gpd = (bGPdata *)ob->data;
const bool is_multiedit = ((GPENCIL_MULTIEDIT_SESSIONS_ON(gpd)) && (!GPENCIL_PLAY_ON(gpd)));
diff --git a/source/blender/blenkernel/intern/ipo.c b/source/blender/blenkernel/intern/ipo.c
index a1f82b1dcb6..8a70f065e40 100644
--- a/source/blender/blenkernel/intern/ipo.c
+++ b/source/blender/blenkernel/intern/ipo.c
@@ -2087,7 +2087,7 @@ void do_versions_ipos_to_animato(Main *bmain)
/* check if object has any animation data */
if (ob->nlastrips.first) {
/* Add AnimData block */
- BKE_animdata_add_id(id);
+ BKE_animdata_ensure_id(id);
/* IPO first to take into any non-NLA'd Object Animation */
if (ob->ipo) {
@@ -2109,7 +2109,7 @@ void do_versions_ipos_to_animato(Main *bmain)
}
else if ((ob->ipo) || (ob->action)) {
/* Add AnimData block */
- AnimData *adt = BKE_animdata_add_id(id);
+ AnimData *adt = BKE_animdata_ensure_id(id);
/* Action first - so that Action name get conserved */
if (ob->action) {
@@ -2133,7 +2133,7 @@ void do_versions_ipos_to_animato(Main *bmain)
/* check PoseChannels for constraints with local data */
if (ob->pose) {
/* Verify if there's AnimData block */
- BKE_animdata_add_id(id);
+ BKE_animdata_ensure_id(id);
for (pchan = ob->pose->chanbase.first; pchan; pchan = pchan->next) {
for (con = pchan->constraints.first; con; con = con->next) {
@@ -2159,7 +2159,7 @@ void do_versions_ipos_to_animato(Main *bmain)
*/
if (con->ipo) {
/* Verify if there's AnimData block, just in case */
- BKE_animdata_add_id(id);
+ BKE_animdata_ensure_id(id);
/* although this was the constraint's local IPO, we still need to provide con
* so that drivers can be added properly...
@@ -2176,7 +2176,7 @@ void do_versions_ipos_to_animato(Main *bmain)
/* check constraint channels - we need to remove them anyway... */
if (ob->constraintChannels.first) {
/* Verify if there's AnimData block */
- BKE_animdata_add_id(id);
+ BKE_animdata_ensure_id(id);
for (conchan = ob->constraintChannels.first; conchan; conchan = conchann) {
/* get pointer to next Constraint Channel */
@@ -2217,7 +2217,7 @@ void do_versions_ipos_to_animato(Main *bmain)
*/
if (key->ipo) {
/* Add AnimData block */
- AnimData *adt = BKE_animdata_add_id(id);
+ AnimData *adt = BKE_animdata_ensure_id(id);
/* Convert Shapekey data... */
ipo_to_animdata(bmain, id, key->ipo, NULL, NULL, NULL);
@@ -2242,7 +2242,7 @@ void do_versions_ipos_to_animato(Main *bmain)
/* we're only interested in the IPO */
if (ma->ipo) {
/* Add AnimData block */
- AnimData *adt = BKE_animdata_add_id(id);
+ AnimData *adt = BKE_animdata_ensure_id(id);
/* Convert Material data... */
ipo_to_animdata(bmain, id, ma->ipo, NULL, NULL, NULL);
@@ -2267,7 +2267,7 @@ void do_versions_ipos_to_animato(Main *bmain)
/* we're only interested in the IPO */
if (wo->ipo) {
/* Add AnimData block */
- AnimData *adt = BKE_animdata_add_id(id);
+ AnimData *adt = BKE_animdata_ensure_id(id);
/* Convert World data... */
ipo_to_animdata(bmain, id, wo->ipo, NULL, NULL, NULL);
@@ -2288,7 +2288,7 @@ void do_versions_ipos_to_animato(Main *bmain)
if (ed && ed->seqbasep) {
Sequence *seq;
- AnimData *adt = BKE_animdata_add_id(id);
+ AnimData *adt = BKE_animdata_ensure_id(id);
SEQ_ALL_BEGIN (ed, seq) {
IpoCurve *icu = (seq->ipo) ? seq->ipo->curve.first : NULL;
@@ -2346,7 +2346,7 @@ void do_versions_ipos_to_animato(Main *bmain)
/* we're only interested in the IPO */
if (te->ipo) {
/* Add AnimData block */
- AnimData *adt = BKE_animdata_add_id(id);
+ AnimData *adt = BKE_animdata_ensure_id(id);
/* Convert Texture data... */
ipo_to_animdata(bmain, id, te->ipo, NULL, NULL, NULL);
@@ -2371,7 +2371,7 @@ void do_versions_ipos_to_animato(Main *bmain)
/* we're only interested in the IPO */
if (ca->ipo) {
/* Add AnimData block */
- AnimData *adt = BKE_animdata_add_id(id);
+ AnimData *adt = BKE_animdata_ensure_id(id);
/* Convert Camera data... */
ipo_to_animdata(bmain, id, ca->ipo, NULL, NULL, NULL);
@@ -2396,7 +2396,7 @@ void do_versions_ipos_to_animato(Main *bmain)
/* we're only interested in the IPO */
if (la->ipo) {
/* Add AnimData block */
- AnimData *adt = BKE_animdata_add_id(id);
+ AnimData *adt = BKE_animdata_ensure_id(id);
/* Convert Light data... */
ipo_to_animdata(bmain, id, la->ipo, NULL, NULL, NULL);
@@ -2421,7 +2421,7 @@ void do_versions_ipos_to_animato(Main *bmain)
/* we're only interested in the IPO */
if (cu->ipo) {
/* Add AnimData block */
- AnimData *adt = BKE_animdata_add_id(id);
+ AnimData *adt = BKE_animdata_ensure_id(id);
/* Convert Curve data... */
ipo_to_animdata(bmain, id, cu->ipo, NULL, NULL, NULL);
diff --git a/source/blender/blenkernel/intern/lattice_deform.c b/source/blender/blenkernel/intern/lattice_deform.c
index 1856a08e198..f9437eeaffa 100644
--- a/source/blender/blenkernel/intern/lattice_deform.c
+++ b/source/blender/blenkernel/intern/lattice_deform.c
@@ -108,7 +108,7 @@ LatticeDeformData *BKE_lattice_deform_data_create(const Object *oblatt, const Ob
invert_m4_m4(imat, latmat);
}
- /* Prefetch latice deform group weights. */
+ /* Prefetch lattice deform group weights. */
int defgrp_index = -1;
const MDeformVert *dvert = BKE_lattice_deform_verts_get(oblatt);
if (lt->vgroup[0] && dvert) {
diff --git a/source/blender/blenkernel/intern/layer_utils.c b/source/blender/blenkernel/intern/layer_utils.c
index 10ab0a06dd0..48179e0c3bf 100644
--- a/source/blender/blenkernel/intern/layer_utils.c
+++ b/source/blender/blenkernel/intern/layer_utils.c
@@ -23,6 +23,7 @@
#include "BLI_array.h"
#include "BKE_collection.h"
+#include "BKE_customdata.h"
#include "BKE_editmesh.h"
#include "BKE_layer.h"
diff --git a/source/blender/blenkernel/intern/lib_id.c b/source/blender/blenkernel/intern/lib_id.c
index c00fba852ef..9d0349a7e89 100644
--- a/source/blender/blenkernel/intern/lib_id.c
+++ b/source/blender/blenkernel/intern/lib_id.c
@@ -1642,9 +1642,8 @@ static bool check_for_dupid(ListBase *lb, ID *id, char *name, ID **r_id_sorting_
* already.
*/
if (!is_orig_name_used) {
- /* Don't bother updating prev_ static variables here, this case is not supposed to happen
- * that often, and is not straight-forward here, so just ignore and reset them to default.
- */
+ /* Don't bother updating `prev_*` static variables here, this case is not supposed to happen
+ * that often, and is not straight-forward here, so just ignore and reset them to default. */
prev_id_type = ID_LINK_PLACEHOLDER;
prev_final_base_name[0] = '\0';
prev_number = MIN_NUMBER - 1;
@@ -1684,7 +1683,7 @@ static bool check_for_dupid(ListBase *lb, ID *id, char *name, ID **r_id_sorting_
continue;
}
- /* Update prev_ static variables, in case next call is for the same type of IDs and with the
+ /* Update `prev_*` static variables, in case next call is for the same type of IDs and with the
* same initial base name, we can skip a lot of above process. */
prev_id_type = id_type;
strcpy(prev_final_base_name, base_name);
diff --git a/source/blender/blenkernel/intern/mesh_boolean_convert.cc b/source/blender/blenkernel/intern/mesh_boolean_convert.cc
index 9bfb01a257c..798d9562150 100644
--- a/source/blender/blenkernel/intern/mesh_boolean_convert.cc
+++ b/source/blender/blenkernel/intern/mesh_boolean_convert.cc
@@ -38,6 +38,7 @@
#include "BLI_mesh_boolean.hh"
#include "BLI_mesh_intersect.hh"
#include "BLI_span.hh"
+#include "BLI_task.hh"
namespace blender::meshintersect {
@@ -309,22 +310,38 @@ static IMesh meshes_to_imesh(Span<const Mesh *> meshes,
clean_obmat(*obmats[mi]);
r_info->to_target_transform[mi] = inv_target_mat * objn_mat;
- /* Skip the matrix multiplication for each point when there is no transform for a mesh,
- * for example when the first mesh is already in the target space. (Note the logic directly
- * above, which uses an identity matrix with a null input transform). */
+ Vector<Vert *> verts(me->totvert);
+ Span<MVert> mverts = Span(me->mvert, me->totvert);
+
+ /* Allocate verts
+ * Skip the matrix multiplication for each point when there is no transform for a mesh,
+ * for example when the first mesh is already in the target space. (Note the logic
+ * directly above, which uses an identity matrix with a null input transform). */
if (obmats[mi] == nullptr) {
- for (const MVert &vert : Span(me->mvert, me->totvert)) {
- const float3 co = float3(vert.co);
- r_info->mesh_to_imesh_vert[v] = arena.add_or_find_vert(mpq3(co.x, co.y, co.z), v);
- ++v;
- }
+ threading::parallel_for(mverts.index_range(), 2048, [&](IndexRange range) {
+ float3 co;
+ for (int i : range) {
+ co = float3(mverts[i].co);
+ mpq3 mco = mpq3(co.x, co.y, co.z);
+ double3 dco(mco[0].get_d(), mco[1].get_d(), mco[2].get_d());
+ verts[i] = new Vert(mco, dco, NO_INDEX, i);
+ }
+ });
}
else {
- for (const MVert &vert : Span(me->mvert, me->totvert)) {
- const float3 co = r_info->to_target_transform[mi] * float3(vert.co);
- r_info->mesh_to_imesh_vert[v] = arena.add_or_find_vert(mpq3(co.x, co.y, co.z), v);
- ++v;
- }
+ threading::parallel_for(mverts.index_range(), 2048, [&](IndexRange range) {
+ float3 co;
+ for (int i : range) {
+ co = r_info->to_target_transform[mi] * float3(mverts[i].co);
+ mpq3 mco = mpq3(co.x, co.y, co.z);
+ double3 dco(mco[0].get_d(), mco[1].get_d(), mco[2].get_d());
+ verts[i] = new Vert(mco, dco, NO_INDEX, i);
+ }
+ });
+ }
+ for (int i : mverts.index_range()) {
+ r_info->mesh_to_imesh_vert[v] = arena.add_or_find_vert(verts[i]);
+ ++v;
}
for (const MPoly &poly : Span(me->mpoly, me->totpoly)) {
diff --git a/source/blender/blenkernel/intern/mesh_evaluate.c b/source/blender/blenkernel/intern/mesh_evaluate.cc
index 7290679bc07..91fd022a316 100644
--- a/source/blender/blenkernel/intern/mesh_evaluate.c
+++ b/source/blender/blenkernel/intern/mesh_evaluate.cc
@@ -23,7 +23,7 @@
* Functions to evaluate mesh data.
*/
-#include <limits.h>
+#include <climits>
#include "MEM_guardedalloc.h"
@@ -200,7 +200,7 @@ float BKE_mesh_calc_poly_area(const MPoly *mpoly, const MLoop *loopstart, const
}
const MLoop *l_iter = loopstart;
- float(*vertexcos)[3] = BLI_array_alloca(vertexcos, (size_t)mpoly->totloop);
+ float(*vertexcos)[3] = (float(*)[3])BLI_array_alloca(vertexcos, (size_t)mpoly->totloop);
/* pack vertex cos into an array for area_poly_v3 */
for (int i = 0; i < mpoly->totloop; i++, l_iter++) {
@@ -236,7 +236,7 @@ float BKE_mesh_calc_poly_uv_area(const MPoly *mpoly, const MLoopUV *uv_array)
int i, l_iter = mpoly->loopstart;
float area;
- float(*vertexcos)[2] = BLI_array_alloca(vertexcos, (size_t)mpoly->totloop);
+ float(*vertexcos)[2] = (float(*)[2])BLI_array_alloca(vertexcos, (size_t)mpoly->totloop);
/* pack vertex cos into an array for area_poly_v2 */
for (i = 0; i < mpoly->totloop; i++, l_iter++) {
@@ -404,7 +404,7 @@ void BKE_mesh_poly_edgehash_insert(EdgeHash *ehash, const MPoly *mp, const MLoop
ml = &ml_next[i - 1]; /* last loop */
while (i-- != 0) {
- BLI_edgehash_reinsert(ehash, ml->v, ml_next->v, NULL);
+ BLI_edgehash_reinsert(ehash, ml->v, ml_next->v, nullptr);
ml = ml_next;
ml_next++;
@@ -676,7 +676,7 @@ void BKE_mesh_calc_volume(const MVert *mverts,
/** \} */
/* -------------------------------------------------------------------- */
-/** \name NGon Tessellation (NGon/Tessface Conversion)
+/** \name NGon Tessellation (NGon to MFace Conversion)
* \{ */
static void bm_corners_to_loops_ex(ID *id,
@@ -692,9 +692,9 @@ static void bm_corners_to_loops_ex(ID *id,
MFace *mf = mface + findex;
for (int i = 0; i < numTex; i++) {
- MTFace *texface = CustomData_get_n(fdata, CD_MTFACE, findex, i);
+ MTFace *texface = (MTFace *)CustomData_get_n(fdata, CD_MTFACE, findex, i);
- MLoopUV *mloopuv = CustomData_get_n(ldata, CD_MLOOPUV, loopstart, i);
+ MLoopUV *mloopuv = (MLoopUV *)CustomData_get_n(ldata, CD_MLOOPUV, loopstart, i);
copy_v2_v2(mloopuv->uv, texface->uv[0]);
mloopuv++;
copy_v2_v2(mloopuv->uv, texface->uv[1]);
@@ -709,8 +709,8 @@ static void bm_corners_to_loops_ex(ID *id,
}
for (int i = 0; i < numCol; i++) {
- MLoopCol *mloopcol = CustomData_get_n(ldata, CD_MLOOPCOL, loopstart, i);
- MCol *mcol = CustomData_get_n(fdata, CD_MCOL, findex, i);
+ MLoopCol *mloopcol = (MLoopCol *)CustomData_get_n(ldata, CD_MLOOPCOL, loopstart, i);
+ MCol *mcol = (MCol *)CustomData_get_n(fdata, CD_MCOL, findex, i);
MESH_MLOOPCOL_FROM_MCOL(mloopcol, &mcol[0]);
mloopcol++;
@@ -725,8 +725,8 @@ static void bm_corners_to_loops_ex(ID *id,
}
if (CustomData_has_layer(fdata, CD_TESSLOOPNORMAL)) {
- float(*lnors)[3] = CustomData_get(ldata, loopstart, CD_NORMAL);
- short(*tlnors)[3] = CustomData_get(fdata, findex, CD_TESSLOOPNORMAL);
+ float(*lnors)[3] = (float(*)[3])CustomData_get(ldata, loopstart, CD_NORMAL);
+ short(*tlnors)[3] = (short(*)[3])CustomData_get(fdata, findex, CD_TESSLOOPNORMAL);
const int max = mf->v4 ? 4 : 3;
for (int i = 0; i < max; i++, lnors++, tlnors++) {
@@ -735,8 +735,8 @@ static void bm_corners_to_loops_ex(ID *id,
}
if (CustomData_has_layer(fdata, CD_MDISPS)) {
- MDisps *ld = CustomData_get(ldata, loopstart, CD_MDISPS);
- MDisps *fd = CustomData_get(fdata, findex, CD_MDISPS);
+ MDisps *ld = (MDisps *)CustomData_get(ldata, loopstart, CD_MDISPS);
+ MDisps *fd = (MDisps *)CustomData_get(fdata, findex, CD_MDISPS);
float(*disps)[3] = fd->disps;
int tot = mf->v4 ? 4 : 3;
int corners;
@@ -750,9 +750,9 @@ static void bm_corners_to_loops_ex(ID *id,
corners = multires_mdisp_corners(fd);
if (corners == 0) {
- /* Empty MDisp layers appear in at least one of the sintel.blend files.
+ /* Empty #MDisp layers appear in at least one of the `sintel.blend` files.
* Not sure why this happens, but it seems fine to just ignore them here.
- * If (corners == 0) for a non-empty layer though, something went wrong. */
+ * If `corners == 0` for a non-empty layer though, something went wrong. */
BLI_assert(fd->totdisp == 0);
}
else {
@@ -767,7 +767,8 @@ static void bm_corners_to_loops_ex(ID *id,
MEM_freeN(ld->disps);
}
- ld->disps = MEM_malloc_arrayN((size_t)side_sq, sizeof(float[3]), "converted loop mdisps");
+ ld->disps = (float(*)[3])MEM_malloc_arrayN(
+ (size_t)side_sq, sizeof(float[3]), "converted loop mdisps");
if (fd->disps) {
memcpy(ld->disps, disps, (size_t)side_sq * sizeof(float[3]));
}
@@ -801,15 +802,16 @@ void BKE_mesh_convert_mfaces_to_mpolys(Mesh *mesh)
/**
* The same as #BKE_mesh_convert_mfaces_to_mpolys
- * but oriented to be used in #do_versions from readfile.c
- * the difference is how active/render/clone/stencil indices are handled here
+ * but oriented to be used in #do_versions from `readfile.c`
+ * the difference is how active/render/clone/stencil indices are handled here.
*
- * normally thay're being set from pdata which totally makes sense for meshes which are already
- * converted to bmesh structures, but when loading older files indices shall be updated in other
- * way around, so newly added pdata and ldata would have this indices set based on fdata layer
+ * normally they're being set from `pdata` which totally makes sense for meshes which are already
+ * converted to #BMesh structures, but when loading older files indices shall be updated in other
+ * way around, so newly added `pdata` and `ldata` would have this indices set
+ * based on `fdata` layer.
*
* this is normally only needed when reading older files,
- * in all other cases #BKE_mesh_convert_mfaces_to_mpolys shall be always used
+ * in all other cases #BKE_mesh_convert_mfaces_to_mpolys shall be always used.
*/
void BKE_mesh_do_versions_convert_mfaces_to_mpolys(Mesh *mesh)
{
@@ -864,7 +866,7 @@ void BKE_mesh_convert_mfaces_to_mpolys_ex(ID *id,
CustomData_free(pdata, totpoly_i);
totpoly = totface_i;
- mpoly = MEM_calloc_arrayN((size_t)totpoly, sizeof(MPoly), "mpoly converted");
+ mpoly = (MPoly *)MEM_calloc_arrayN((size_t)totpoly, sizeof(MPoly), "mpoly converted");
CustomData_add_layer(pdata, CD_MPOLY, CD_ASSIGN, mpoly, totpoly);
numTex = CustomData_number_of_layers(fdata, CD_MTFACE);
@@ -876,7 +878,7 @@ void BKE_mesh_convert_mfaces_to_mpolys_ex(ID *id,
totloop += mf->v4 ? 4 : 3;
}
- mloop = MEM_calloc_arrayN((size_t)totloop, sizeof(MLoop), "mloop converted");
+ mloop = (MLoop *)MEM_calloc_arrayN((size_t)totloop, sizeof(MLoop), "mloop converted");
CustomData_add_layer(ldata, CD_MLOOP, CD_ASSIGN, mloop, totloop);
@@ -900,7 +902,7 @@ void BKE_mesh_convert_mfaces_to_mpolys_ex(ID *id,
me->flag &= ~ME_FGON;
}
- polyindex = CustomData_get_layer(fdata, CD_ORIGINDEX);
+ polyindex = (int *)CustomData_get_layer(fdata, CD_ORIGINDEX);
j = 0; /* current loop index */
ml = mloop;
@@ -946,7 +948,7 @@ void BKE_mesh_convert_mfaces_to_mpolys_ex(ID *id,
/* NOTE: we don't convert NGons at all, these are not even real ngons,
* they have their own UV's, colors etc - its more an editing feature. */
- BLI_edgehash_free(eh, NULL);
+ BLI_edgehash_free(eh, nullptr);
*r_totpoly = totpoly;
*r_totloop = totloop;
@@ -1050,8 +1052,8 @@ void BKE_mesh_polygon_flip_ex(MPoly *mpoly,
void BKE_mesh_polygon_flip(MPoly *mpoly, MLoop *mloop, CustomData *ldata)
{
- MDisps *mdisp = CustomData_get_layer(ldata, CD_MDISPS);
- BKE_mesh_polygon_flip_ex(mpoly, mloop, ldata, NULL, mdisp, true);
+ MDisps *mdisp = (MDisps *)CustomData_get_layer(ldata, CD_MDISPS);
+ BKE_mesh_polygon_flip_ex(mpoly, mloop, ldata, nullptr, mdisp, true);
}
/**
@@ -1061,12 +1063,12 @@ void BKE_mesh_polygon_flip(MPoly *mpoly, MLoop *mloop, CustomData *ldata)
*/
void BKE_mesh_polygons_flip(MPoly *mpoly, MLoop *mloop, CustomData *ldata, int totpoly)
{
- MDisps *mdisp = CustomData_get_layer(ldata, CD_MDISPS);
+ MDisps *mdisp = (MDisps *)CustomData_get_layer(ldata, CD_MDISPS);
MPoly *mp;
int i;
for (mp = mpoly, i = 0; i < totpoly; mp++, i++) {
- BKE_mesh_polygon_flip_ex(mp, mloop, ldata, NULL, mdisp, true);
+ BKE_mesh_polygon_flip_ex(mp, mloop, ldata, nullptr, mdisp, true);
}
}
@@ -1277,7 +1279,7 @@ void BKE_mesh_calc_relative_deform(const MPoly *mpoly,
const MPoly *mp;
int i;
- int *vert_accum = MEM_calloc_arrayN((size_t)totvert, sizeof(*vert_accum), __func__);
+ int *vert_accum = (int *)MEM_calloc_arrayN((size_t)totvert, sizeof(*vert_accum), __func__);
memset(vert_cos_new, '\0', sizeof(*vert_cos_new) * (size_t)totvert);
diff --git a/source/blender/blenkernel/intern/mesh_mapping.c b/source/blender/blenkernel/intern/mesh_mapping.c
index 9a3333fce6c..ca6c60557a6 100644
--- a/source/blender/blenkernel/intern/mesh_mapping.c
+++ b/source/blender/blenkernel/intern/mesh_mapping.c
@@ -998,7 +998,7 @@ void BKE_mesh_loop_islands_add(MeshIslandStore *island_store,
}
/* TODO: I'm not sure edge seam flag is enough to define UV islands?
- * Maybe we should also consider UVmaps values
+ * Maybe we should also consider UV-maps values
* themselves (i.e. different UV-edges for a same mesh-edge => boundary edge too?).
* Would make things much more complex though,
* and each UVMap would then need its own mesh mapping, not sure we want that at all!
diff --git a/source/blender/blenkernel/intern/mesh_normals.c b/source/blender/blenkernel/intern/mesh_normals.cc
index 89fd7f92d94..2fe132fc684 100644
--- a/source/blender/blenkernel/intern/mesh_normals.c
+++ b/source/blender/blenkernel/intern/mesh_normals.cc
@@ -25,7 +25,7 @@
* \see bmesh_mesh_normals.c for the equivalent #BMesh functionality.
*/
-#include <limits.h>
+#include <climits>
#include "CLG_log.h"
@@ -90,15 +90,15 @@ void BKE_mesh_calc_normals_mapping_simple(struct Mesh *mesh)
mesh->mpoly,
mesh->totloop,
mesh->totpoly,
- NULL,
+ nullptr,
mesh->mface,
mesh->totface,
- NULL,
- NULL,
+ nullptr,
+ nullptr,
only_face_normals);
}
-/* Calculate vertex and face normals, face normals are returned in *r_faceNors if non-NULL
+/* Calculate vertex and face normals, face normals are returned in *r_faceNors if non-nullptr
* and vertex normals are stored in actual mverts.
*/
void BKE_mesh_calc_normals_mapping(MVert *mverts,
@@ -150,13 +150,13 @@ void BKE_mesh_calc_normals_mapping_ex(MVert *mverts,
}
/* if we are not calculating verts and no verts were passes then we have nothing to do */
- if ((only_face_normals == true) && (r_polyNors == NULL) && (r_faceNors == NULL)) {
+ if ((only_face_normals == true) && (r_polyNors == nullptr) && (r_faceNors == nullptr)) {
CLOG_WARN(&LOG, "called with nothing to do");
return;
}
if (!pnors) {
- pnors = MEM_calloc_arrayN((size_t)numPolys, sizeof(float[3]), __func__);
+ pnors = (float(*)[3])MEM_calloc_arrayN((size_t)numPolys, sizeof(float[3]), __func__);
}
/* NO NEED TO ALLOC YET */
/* if (!fnors) fnors = MEM_calloc_arrayN(numFaces, sizeof(float[3]), "face nors mesh.c"); */
@@ -165,7 +165,7 @@ void BKE_mesh_calc_normals_mapping_ex(MVert *mverts,
/* vertex normals are optional, they require some extra calculations,
* so make them optional */
BKE_mesh_calc_normals_poly(
- mverts, NULL, numVerts, mloop, mpolys, numLoops, numPolys, pnors, false);
+ mverts, nullptr, numVerts, mloop, mpolys, numLoops, numPolys, pnors, false);
}
else {
/* only calc poly normals */
@@ -177,7 +177,7 @@ void BKE_mesh_calc_normals_mapping_ex(MVert *mverts,
if (origIndexFace &&
/* fnors == r_faceNors */ /* NO NEED TO ALLOC YET */
- fnors != NULL &&
+ fnors != nullptr &&
numFaces) {
const MFace *mf = mfaces;
for (int i = 0; i < numFaces; i++, mf++, origIndexFace++) {
@@ -196,23 +196,23 @@ void BKE_mesh_calc_normals_mapping_ex(MVert *mverts,
}
/* if (fnors != r_faceNors) MEM_freeN(fnors); */ /* NO NEED TO ALLOC YET */
- fnors = pnors = NULL;
+ fnors = pnors = nullptr;
}
-typedef struct MeshCalcNormalsData {
+struct MeshCalcNormalsData {
const MPoly *mpolys;
const MLoop *mloop;
MVert *mverts;
float (*pnors)[3];
float (*lnors_weighted)[3];
float (*vnors)[3];
-} MeshCalcNormalsData;
+};
static void mesh_calc_normals_poly_cb(void *__restrict userdata,
const int pidx,
const TaskParallelTLS *__restrict UNUSED(tls))
{
- MeshCalcNormalsData *data = userdata;
+ MeshCalcNormalsData *data = (MeshCalcNormalsData *)userdata;
const MPoly *mp = &data->mpolys[pidx];
BKE_mesh_calc_poly_normal(mp, data->mloop + mp->loopstart, data->mverts, data->pnors[pidx]);
@@ -222,7 +222,7 @@ static void mesh_calc_normals_poly_prepare_cb(void *__restrict userdata,
const int pidx,
const TaskParallelTLS *__restrict UNUSED(tls))
{
- MeshCalcNormalsData *data = userdata;
+ MeshCalcNormalsData *data = (MeshCalcNormalsData *)userdata;
const MPoly *mp = &data->mpolys[pidx];
const MLoop *ml = &data->mloop[mp->loopstart];
const MVert *mverts = data->mverts;
@@ -232,7 +232,7 @@ static void mesh_calc_normals_poly_prepare_cb(void *__restrict userdata,
float(*lnors_weighted)[3] = data->lnors_weighted;
const int nverts = mp->totloop;
- float(*edgevecbuf)[3] = BLI_array_alloca(edgevecbuf, (size_t)nverts);
+ float(*edgevecbuf)[3] = (float(*)[3])BLI_array_alloca(edgevecbuf, (size_t)nverts);
/* Polygon Normal and edge-vector */
/* inline version of #BKE_mesh_calc_poly_normal, also does edge-vectors */
@@ -285,7 +285,7 @@ static void mesh_calc_normals_poly_finalize_cb(void *__restrict userdata,
const int vidx,
const TaskParallelTLS *__restrict UNUSED(tls))
{
- MeshCalcNormalsData *data = userdata;
+ MeshCalcNormalsData *data = (MeshCalcNormalsData *)userdata;
MVert *mv = &data->mverts[vidx];
float *no = data->vnors[vidx];
@@ -315,42 +315,40 @@ void BKE_mesh_calc_normals_poly(MVert *mverts,
settings.min_iter_per_thread = 1024;
if (only_face_normals) {
- BLI_assert((pnors != NULL) || (numPolys == 0));
- BLI_assert(r_vertnors == NULL);
-
- MeshCalcNormalsData data = {
- .mpolys = mpolys,
- .mloop = mloop,
- .mverts = mverts,
- .pnors = pnors,
- };
+ BLI_assert((pnors != nullptr) || (numPolys == 0));
+ BLI_assert(r_vertnors == nullptr);
+
+ MeshCalcNormalsData data;
+ data.mpolys = mpolys;
+ data.mloop = mloop;
+ data.mverts = mverts;
+ data.pnors = pnors;
BLI_task_parallel_range(0, numPolys, &data, mesh_calc_normals_poly_cb, &settings);
return;
}
float(*vnors)[3] = r_vertnors;
- float(*lnors_weighted)[3] = MEM_malloc_arrayN(
+ float(*lnors_weighted)[3] = (float(*)[3])MEM_malloc_arrayN(
(size_t)numLoops, sizeof(*lnors_weighted), __func__);
bool free_vnors = false;
/* first go through and calculate normals for all the polys */
- if (vnors == NULL) {
- vnors = MEM_calloc_arrayN((size_t)numVerts, sizeof(*vnors), __func__);
+ if (vnors == nullptr) {
+ vnors = (float(*)[3])MEM_calloc_arrayN((size_t)numVerts, sizeof(*vnors), __func__);
free_vnors = true;
}
else {
memset(vnors, 0, sizeof(*vnors) * (size_t)numVerts);
}
- MeshCalcNormalsData data = {
- .mpolys = mpolys,
- .mloop = mloop,
- .mverts = mverts,
- .pnors = pnors,
- .lnors_weighted = lnors_weighted,
- .vnors = vnors,
- };
+ MeshCalcNormalsData data;
+ data.mpolys = mpolys;
+ data.mloop = mloop;
+ data.mverts = mverts;
+ data.pnors = pnors;
+ data.lnors_weighted = lnors_weighted;
+ data.vnors = vnors;
/* Compute poly normals, and prepare weighted loop normals. */
BLI_task_parallel_range(0, numPolys, &data, mesh_calc_normals_poly_prepare_cb, &settings);
@@ -400,19 +398,21 @@ void BKE_mesh_ensure_normals_for_display(Mesh *mesh)
}
}
- float(*poly_nors)[3] = CustomData_get_layer(&mesh->pdata, CD_NORMAL);
+ float(*poly_nors)[3] = (float(*)[3])CustomData_get_layer(&mesh->pdata, CD_NORMAL);
const bool do_vert_normals = (mesh->runtime.cd_dirty_vert & CD_MASK_NORMAL) != 0;
- const bool do_poly_normals = (mesh->runtime.cd_dirty_poly & CD_MASK_NORMAL || poly_nors == NULL);
+ const bool do_poly_normals = (mesh->runtime.cd_dirty_poly & CD_MASK_NORMAL ||
+ poly_nors == nullptr);
if (do_vert_normals || do_poly_normals) {
- const bool do_add_poly_nors_cddata = (poly_nors == NULL);
+ const bool do_add_poly_nors_cddata = (poly_nors == nullptr);
if (do_add_poly_nors_cddata) {
- poly_nors = MEM_malloc_arrayN((size_t)mesh->totpoly, sizeof(*poly_nors), __func__);
+ poly_nors = (float(*)[3])MEM_malloc_arrayN(
+ (size_t)mesh->totpoly, sizeof(*poly_nors), __func__);
}
/* calculate poly/vert normals */
BKE_mesh_calc_normals_poly(mesh->mvert,
- NULL,
+ nullptr,
mesh->totvert,
mesh->mloop,
mesh->mpoly,
@@ -438,13 +438,13 @@ void BKE_mesh_calc_normals(Mesh *mesh)
TIMEIT_START_AVERAGED(BKE_mesh_calc_normals);
#endif
BKE_mesh_calc_normals_poly(mesh->mvert,
- NULL,
+ nullptr,
mesh->totvert,
mesh->mloop,
mesh->mpoly,
mesh->totloop,
mesh->totpoly,
- NULL,
+ nullptr,
false);
#ifdef DEBUG_TIME
TIMEIT_END_AVERAGED(BKE_mesh_calc_normals);
@@ -459,10 +459,10 @@ void BKE_mesh_calc_normals_looptri(MVert *mverts,
int looptri_num,
float (*r_tri_nors)[3])
{
- float(*tnorms)[3] = MEM_calloc_arrayN((size_t)numVerts, sizeof(*tnorms), "tnorms");
- float(*fnors)[3] = (r_tri_nors) ?
- r_tri_nors :
- MEM_calloc_arrayN((size_t)looptri_num, sizeof(*fnors), "meshnormals");
+ float(*tnorms)[3] = (float(*)[3])MEM_calloc_arrayN((size_t)numVerts, sizeof(*tnorms), "tnorms");
+ float(*fnors)[3] = (r_tri_nors) ? r_tri_nors :
+ (float(*)[3])MEM_calloc_arrayN(
+ (size_t)looptri_num, sizeof(*fnors), "meshnormals");
if (!tnorms || !fnors) {
goto cleanup;
@@ -519,9 +519,10 @@ void BKE_lnor_spacearr_init(MLoopNorSpaceArray *lnors_spacearr,
lnors_spacearr->mem = BLI_memarena_new(BLI_MEMARENA_STD_BUFSIZE, __func__);
}
mem = lnors_spacearr->mem;
- lnors_spacearr->lspacearr = BLI_memarena_calloc(mem,
- sizeof(MLoopNorSpace *) * (size_t)numLoops);
- lnors_spacearr->loops_pool = BLI_memarena_alloc(mem, sizeof(LinkNode) * (size_t)numLoops);
+ lnors_spacearr->lspacearr = (MLoopNorSpace **)BLI_memarena_calloc(
+ mem, sizeof(MLoopNorSpace *) * (size_t)numLoops);
+ lnors_spacearr->loops_pool = (LinkNode *)BLI_memarena_alloc(
+ mem, sizeof(LinkNode) * (size_t)numLoops);
lnors_spacearr->num_spaces = 0;
}
@@ -532,9 +533,9 @@ void BKE_lnor_spacearr_init(MLoopNorSpaceArray *lnors_spacearr,
void BKE_lnor_spacearr_clear(MLoopNorSpaceArray *lnors_spacearr)
{
lnors_spacearr->num_spaces = 0;
- lnors_spacearr->lspacearr = NULL;
- lnors_spacearr->loops_pool = NULL;
- if (lnors_spacearr->mem != NULL) {
+ lnors_spacearr->lspacearr = nullptr;
+ lnors_spacearr->loops_pool = nullptr;
+ if (lnors_spacearr->mem != nullptr) {
BLI_memarena_clear(lnors_spacearr->mem);
}
}
@@ -542,16 +543,16 @@ void BKE_lnor_spacearr_clear(MLoopNorSpaceArray *lnors_spacearr)
void BKE_lnor_spacearr_free(MLoopNorSpaceArray *lnors_spacearr)
{
lnors_spacearr->num_spaces = 0;
- lnors_spacearr->lspacearr = NULL;
- lnors_spacearr->loops_pool = NULL;
+ lnors_spacearr->lspacearr = nullptr;
+ lnors_spacearr->loops_pool = nullptr;
BLI_memarena_free(lnors_spacearr->mem);
- lnors_spacearr->mem = NULL;
+ lnors_spacearr->mem = nullptr;
}
MLoopNorSpace *BKE_lnor_space_create(MLoopNorSpaceArray *lnors_spacearr)
{
lnors_spacearr->num_spaces++;
- return BLI_memarena_calloc(lnors_spacearr->mem, sizeof(MLoopNorSpace));
+ return (MLoopNorSpace *)BLI_memarena_calloc(lnors_spacearr->mem, sizeof(MLoopNorSpace));
}
/* This threshold is a bit touchy (usual float precision issue), this value seems OK. */
@@ -592,7 +593,7 @@ void BKE_lnor_space_define(MLoopNorSpace *lnor_space,
float alpha = 0.0f;
int nbr = 0;
while (!BLI_stack_is_empty(edge_vectors)) {
- const float *vec = BLI_stack_peek(edge_vectors);
+ const float *vec = (const float *)BLI_stack_peek(edge_vectors);
alpha += saacosf(dot_v3v3(vec, lnor));
BLI_stack_discard(edge_vectors);
nbr++;
@@ -637,10 +638,10 @@ void BKE_lnor_space_define(MLoopNorSpace *lnor_space,
/**
* Add a new given loop to given lnor_space.
* Depending on \a lnor_space->data_type, we expect \a bm_loop to be a pointer to BMLoop struct
- * (in case of BMLOOP_PTR), or NULL (in case of LOOP_INDEX), loop index is then stored in pointer.
- * If \a is_single is set, the BMLoop or loop index is directly stored in \a lnor_space->loops
- * pointer (since there is only one loop in this fan),
- * else it is added to the linked list of loops in the fan.
+ * (in case of BMLOOP_PTR), or nullptr (in case of LOOP_INDEX), loop index is then stored in
+ * pointer. If \a is_single is set, the BMLoop or loop index is directly stored in \a
+ * lnor_space->loops pointer (since there is only one loop in this fan), else it is added to the
+ * linked list of loops in the fan.
*/
void BKE_lnor_space_add_loop(MLoopNorSpaceArray *lnors_spacearr,
MLoopNorSpace *lnor_space,
@@ -648,17 +649,17 @@ void BKE_lnor_space_add_loop(MLoopNorSpaceArray *lnors_spacearr,
void *bm_loop,
const bool is_single)
{
- BLI_assert((lnors_spacearr->data_type == MLNOR_SPACEARR_LOOP_INDEX && bm_loop == NULL) ||
- (lnors_spacearr->data_type == MLNOR_SPACEARR_BMLOOP_PTR && bm_loop != NULL));
+ BLI_assert((lnors_spacearr->data_type == MLNOR_SPACEARR_LOOP_INDEX && bm_loop == nullptr) ||
+ (lnors_spacearr->data_type == MLNOR_SPACEARR_BMLOOP_PTR && bm_loop != nullptr));
lnors_spacearr->lspacearr[ml_index] = lnor_space;
- if (bm_loop == NULL) {
+ if (bm_loop == nullptr) {
bm_loop = POINTER_FROM_INT(ml_index);
}
if (is_single) {
- BLI_assert(lnor_space->loops == NULL);
+ BLI_assert(lnor_space->loops == nullptr);
lnor_space->flags |= MLNOR_SPACE_IS_SINGLE;
- lnor_space->loops = bm_loop;
+ lnor_space->loops = (LinkNode *)bm_loop;
}
else {
BLI_assert((lnor_space->flags & MLNOR_SPACE_IS_SINGLE) == 0);
@@ -715,7 +716,8 @@ void BKE_lnor_space_custom_normal_to_data(MLoopNorSpace *lnor_space,
const float custom_lnor[3],
short r_clnor_data[2])
{
- /* We use null vector as NOP custom normal (can be simpler than giving auto-computed `lnor`). */
+ /* We use nullptr vector as NOP custom normal (can be simpler than giving auto-computed `lnor`).
+ */
if (is_zero_v3(custom_lnor) || compare_v3v3(lnor_space->vec_lnor, custom_lnor, 1e-4f)) {
r_clnor_data[0] = r_clnor_data[1] = 0;
return;
@@ -765,7 +767,7 @@ void BKE_lnor_space_custom_normal_to_data(MLoopNorSpace *lnor_space,
#define LOOP_SPLIT_TASK_BLOCK_SIZE 1024
-typedef struct LoopSplitTaskData {
+struct LoopSplitTaskData {
/* Specific to each instance (each task). */
/** We have to create those outside of tasks, since #MemArena is not thread-safe. */
@@ -784,9 +786,9 @@ typedef struct LoopSplitTaskData {
BLI_Stack *edge_vectors;
char pad_c;
-} LoopSplitTaskData;
+};
-typedef struct LoopSplitTaskDataCommon {
+struct LoopSplitTaskDataCommon {
/* Read/write.
* Note we do not need to protect it, though, since two different tasks will *always* affect
* different elements in the arrays. */
@@ -806,7 +808,7 @@ typedef struct LoopSplitTaskDataCommon {
int numEdges;
int numLoops;
int numPolys;
-} LoopSplitTaskDataCommon;
+};
#define INDEX_UNSET INT_MIN
#define INDEX_INVALID -1
@@ -827,13 +829,13 @@ static void mesh_edges_sharp_tag(LoopSplitTaskDataCommon *data,
const int numEdges = data->numEdges;
const int numPolys = data->numPolys;
- float(*loopnors)[3] = data->loopnors; /* NOTE: loopnors may be NULL here. */
+ float(*loopnors)[3] = data->loopnors; /* NOTE: loopnors may be nullptr here. */
const float(*polynors)[3] = data->polynors;
int(*edge_to_loops)[2] = data->edge_to_loops;
int *loop_to_poly = data->loop_to_poly;
- BLI_bitmap *sharp_edges = do_sharp_edges_tag ? BLI_BITMAP_NEW(numEdges, __func__) : NULL;
+ BLI_bitmap *sharp_edges = do_sharp_edges_tag ? BLI_BITMAP_NEW(numEdges, __func__) : nullptr;
const MPoly *mp;
int mp_index;
@@ -943,22 +945,22 @@ void BKE_edges_sharp_from_angle_set(const struct MVert *mverts,
}
/* Mapping edge -> loops. See BKE_mesh_normals_loop_split() for details. */
- int(*edge_to_loops)[2] = MEM_calloc_arrayN((size_t)numEdges, sizeof(*edge_to_loops), __func__);
+ int(*edge_to_loops)[2] = (int(*)[2])MEM_calloc_arrayN(
+ (size_t)numEdges, sizeof(*edge_to_loops), __func__);
/* Simple mapping from a loop to its polygon index. */
- int *loop_to_poly = MEM_malloc_arrayN((size_t)numLoops, sizeof(*loop_to_poly), __func__);
-
- LoopSplitTaskDataCommon common_data = {
- .mverts = mverts,
- .medges = medges,
- .mloops = mloops,
- .mpolys = mpolys,
- .edge_to_loops = edge_to_loops,
- .loop_to_poly = loop_to_poly,
- .polynors = polynors,
- .numEdges = numEdges,
- .numPolys = numPolys,
- };
+ int *loop_to_poly = (int *)MEM_malloc_arrayN((size_t)numLoops, sizeof(*loop_to_poly), __func__);
+
+ LoopSplitTaskDataCommon common_data;
+ common_data.mverts = mverts;
+ common_data.medges = medges;
+ common_data.mloops = mloops;
+ common_data.mpolys = mpolys;
+ common_data.edge_to_loops = edge_to_loops;
+ common_data.loop_to_poly = loop_to_poly;
+ common_data.polynors = polynors;
+ common_data.numEdges = numEdges;
+ common_data.numPolys = numPolys;
mesh_edges_sharp_tag(&common_data, true, split_angle, true);
@@ -1065,10 +1067,10 @@ static void split_loop_nor_single_do(LoopSplitTaskDataCommon *common_data, LoopS
sub_v3_v3v3(vec_prev, mv_3->co, mv_pivot->co);
normalize_v3(vec_prev);
- BKE_lnor_space_define(lnor_space, *lnor, vec_curr, vec_prev, NULL);
+ BKE_lnor_space_define(lnor_space, *lnor, vec_curr, vec_prev, nullptr);
/* We know there is only one loop in this space,
* no need to create a linklist in this case... */
- BKE_lnor_space_add_loop(lnors_spacearr, lnor_space, ml_curr_index, NULL, true);
+ BKE_lnor_space_add_loop(lnors_spacearr, lnor_space, ml_curr_index, nullptr, true);
if (clnors_data) {
BKE_lnor_space_custom_data_to_normal(lnor_space, clnors_data[ml_curr_index], *lnor);
@@ -1125,7 +1127,7 @@ static void split_loop_nor_fan_do(LoopSplitTaskDataCommon *common_data, LoopSpli
/* We validate clnors data on the fly - cheapest way to do! */
int clnors_avg[2] = {0, 0};
- short(*clnor_ref)[2] = NULL;
+ short(*clnor_ref)[2] = nullptr;
int clnors_nbr = 0;
bool clnors_invalid = false;
@@ -1205,7 +1207,7 @@ static void split_loop_nor_fan_do(LoopSplitTaskDataCommon *common_data, LoopSpli
if (lnors_spacearr) {
/* Assign current lnor space to current 'vertex' loop. */
- BKE_lnor_space_add_loop(lnors_spacearr, lnor_space, mlfan_vert_index, NULL, false);
+ BKE_lnor_space_add_loop(lnors_spacearr, lnor_space, mlfan_vert_index, nullptr, false);
if (me_curr != me_org) {
/* We store here all edges-normalized vectors processed. */
BLI_stack_push(edge_vectors, vec_curr);
@@ -1261,7 +1263,7 @@ static void split_loop_nor_fan_do(LoopSplitTaskDataCommon *common_data, LoopSpli
if (G.debug & G_DEBUG) {
printf("Invalid clnors in this fan!\n");
}
- while ((clnor = BLI_SMALLSTACK_POP(clnors))) {
+ while ((clnor = (short *)BLI_SMALLSTACK_POP(clnors))) {
// print_v2("org clnor", clnor);
clnor[0] = (short)clnors_avg[0];
clnor[1] = (short)clnors_avg[1];
@@ -1280,7 +1282,7 @@ static void split_loop_nor_fan_do(LoopSplitTaskDataCommon *common_data, LoopSpli
/* Copy back the final computed normal into all related loop-normals. */
float *nor;
- while ((nor = BLI_SMALLSTACK_POP(normal))) {
+ while ((nor = (float *)BLI_SMALLSTACK_POP(normal))) {
copy_v3_v3(nor, lnor);
}
}
@@ -1295,7 +1297,7 @@ static void loop_split_worker_do(LoopSplitTaskDataCommon *common_data,
{
BLI_assert(data->ml_curr);
if (data->e2l_prev) {
- BLI_assert((edge_vectors == NULL) || BLI_stack_is_empty(edge_vectors));
+ BLI_assert((edge_vectors == nullptr) || BLI_stack_is_empty(edge_vectors));
data->edge_vectors = edge_vectors;
split_loop_nor_fan_do(common_data, data);
}
@@ -1307,21 +1309,21 @@ static void loop_split_worker_do(LoopSplitTaskDataCommon *common_data,
static void loop_split_worker(TaskPool *__restrict pool, void *taskdata)
{
- LoopSplitTaskDataCommon *common_data = BLI_task_pool_user_data(pool);
- LoopSplitTaskData *data = taskdata;
+ LoopSplitTaskDataCommon *common_data = (LoopSplitTaskDataCommon *)BLI_task_pool_user_data(pool);
+ LoopSplitTaskData *data = (LoopSplitTaskData *)taskdata;
/* Temp edge vectors stack, only used when computing lnor spacearr. */
BLI_Stack *edge_vectors = common_data->lnors_spacearr ?
BLI_stack_new(sizeof(float[3]), __func__) :
- NULL;
+ nullptr;
#ifdef DEBUG_TIME
TIMEIT_START_AVERAGED(loop_split_worker);
#endif
for (int i = 0; i < LOOP_SPLIT_TASK_BLOCK_SIZE; i++, data++) {
- /* A NULL ml_curr is used to tag ended data! */
- if (data->ml_curr == NULL) {
+ /* A nullptr ml_curr is used to tag ended data! */
+ if (data->ml_curr == nullptr) {
break;
}
@@ -1434,12 +1436,12 @@ static void loop_split_generator(TaskPool *pool, LoopSplitTaskDataCommon *common
BLI_bitmap *skip_loops = BLI_BITMAP_NEW(numLoops, __func__);
- LoopSplitTaskData *data_buff = NULL;
+ LoopSplitTaskData *data_buff = nullptr;
int data_idx = 0;
/* Temp edge vectors stack, only used when computing lnor spacearr
* (and we are not multi-threading). */
- BLI_Stack *edge_vectors = NULL;
+ BLI_Stack *edge_vectors = nullptr;
#ifdef DEBUG_TIME
TIMEIT_START_AVERAGED(loop_split_generator);
@@ -1508,7 +1510,7 @@ static void loop_split_generator(TaskPool *pool, LoopSplitTaskDataCommon *common
if (pool) {
if (data_idx == 0) {
- data_buff = MEM_calloc_arrayN(
+ data_buff = (LoopSplitTaskData *)MEM_calloc_arrayN(
LOOP_SPLIT_TASK_BLOCK_SIZE, sizeof(*data_buff), __func__);
}
data = &data_buff[data_idx];
@@ -1525,7 +1527,7 @@ static void loop_split_generator(TaskPool *pool, LoopSplitTaskDataCommon *common
data->ml_curr_index = ml_curr_index;
#if 0 /* Not needed for 'single' loop. */
data->ml_prev_index = ml_prev_index;
- data->e2l_prev = NULL; /* Tag as 'single' task. */
+ data->e2l_prev = nullptr; /* Tag as 'single' task. */
#endif
data->mp_index = mp_index;
if (lnors_spacearr) {
@@ -1559,7 +1561,7 @@ static void loop_split_generator(TaskPool *pool, LoopSplitTaskDataCommon *common
if (pool) {
data_idx++;
if (data_idx == LOOP_SPLIT_TASK_BLOCK_SIZE) {
- BLI_task_pool_push(pool, loop_split_worker, data_buff, true, NULL);
+ BLI_task_pool_push(pool, loop_split_worker, data_buff, true, nullptr);
data_idx = 0;
}
}
@@ -1573,10 +1575,10 @@ static void loop_split_generator(TaskPool *pool, LoopSplitTaskDataCommon *common
}
}
- /* Last block of data... Since it is calloc'ed and we use first NULL item as stopper,
+ /* Last block of data... Since it is calloc'ed and we use first nullptr item as stopper,
* everything is fine. */
if (pool && data_idx) {
- BLI_task_pool_push(pool, loop_split_worker, data_buff, true, NULL);
+ BLI_task_pool_push(pool, loop_split_worker, data_buff, true, nullptr);
}
if (edge_vectors) {
@@ -1659,17 +1661,18 @@ void BKE_mesh_normals_loop_split(const MVert *mverts,
* However, if needed, we can store the negated value of loop index instead of INDEX_INVALID
* to retrieve the real value later in code).
* Note also that loose edges always have both values set to 0! */
- int(*edge_to_loops)[2] = MEM_calloc_arrayN((size_t)numEdges, sizeof(*edge_to_loops), __func__);
+ int(*edge_to_loops)[2] = (int(*)[2])MEM_calloc_arrayN(
+ (size_t)numEdges, sizeof(*edge_to_loops), __func__);
/* Simple mapping from a loop to its polygon index. */
- int *loop_to_poly = r_loop_to_poly ?
- r_loop_to_poly :
- MEM_malloc_arrayN((size_t)numLoops, sizeof(*loop_to_poly), __func__);
+ int *loop_to_poly = r_loop_to_poly ? r_loop_to_poly :
+ (int *)MEM_malloc_arrayN(
+ (size_t)numLoops, sizeof(*loop_to_poly), __func__);
/* When using custom loop normals, disable the angle feature! */
- const bool check_angle = (split_angle < (float)M_PI) && (clnors_data == NULL);
+ const bool check_angle = (split_angle < (float)M_PI) && (clnors_data == nullptr);
- MLoopNorSpaceArray _lnors_spacearr = {NULL};
+ MLoopNorSpaceArray _lnors_spacearr = {nullptr};
#ifdef DEBUG_TIME
TIMEIT_START_AVERAGED(BKE_mesh_normals_loop_split);
@@ -1684,28 +1687,27 @@ void BKE_mesh_normals_loop_split(const MVert *mverts,
}
/* Init data common to all tasks. */
- LoopSplitTaskDataCommon common_data = {
- .lnors_spacearr = r_lnors_spacearr,
- .loopnors = r_loopnors,
- .clnors_data = clnors_data,
- .mverts = mverts,
- .medges = medges,
- .mloops = mloops,
- .mpolys = mpolys,
- .edge_to_loops = edge_to_loops,
- .loop_to_poly = loop_to_poly,
- .polynors = polynors,
- .numEdges = numEdges,
- .numLoops = numLoops,
- .numPolys = numPolys,
- };
+ LoopSplitTaskDataCommon common_data;
+ common_data.lnors_spacearr = r_lnors_spacearr;
+ common_data.loopnors = r_loopnors;
+ common_data.clnors_data = clnors_data;
+ common_data.mverts = mverts;
+ common_data.medges = medges;
+ common_data.mloops = mloops;
+ common_data.mpolys = mpolys;
+ common_data.edge_to_loops = edge_to_loops;
+ common_data.loop_to_poly = loop_to_poly;
+ common_data.polynors = polynors;
+ common_data.numEdges = numEdges;
+ common_data.numLoops = numLoops;
+ common_data.numPolys = numPolys;
/* This first loop check which edges are actually smooth, and compute edge vectors. */
mesh_edges_sharp_tag(&common_data, check_angle, split_angle, false);
if (numLoops < LOOP_SPLIT_TASK_BLOCK_SIZE * 8) {
/* Not enough loops to be worth the whole threading overhead... */
- loop_split_generator(NULL, &common_data);
+ loop_split_generator(nullptr, &common_data);
}
else {
TaskPool *task_pool = BLI_task_pool_create(&common_data, TASK_PRIORITY_HIGH);
@@ -1766,10 +1768,10 @@ static void mesh_normals_loop_custom_set(const MVert *mverts,
* (and perhaps from some editing tools later?).
* So better to keep some simplicity here, and just call BKE_mesh_normals_loop_split() twice!
*/
- MLoopNorSpaceArray lnors_spacearr = {NULL};
+ MLoopNorSpaceArray lnors_spacearr = {nullptr};
BLI_bitmap *done_loops = BLI_BITMAP_NEW((size_t)numLoops, __func__);
- float(*lnors)[3] = MEM_calloc_arrayN((size_t)numLoops, sizeof(*lnors), __func__);
- int *loop_to_poly = MEM_malloc_arrayN((size_t)numLoops, sizeof(int), __func__);
+ float(*lnors)[3] = (float(*)[3])MEM_calloc_arrayN((size_t)numLoops, sizeof(*lnors), __func__);
+ int *loop_to_poly = (int *)MEM_malloc_arrayN((size_t)numLoops, sizeof(int), __func__);
/* In this case we always consider split nors as ON,
* and do not want to use angle to define smooth fans! */
const bool use_split_normals = true;
@@ -1791,7 +1793,7 @@ static void mesh_normals_loop_custom_set(const MVert *mverts,
use_split_normals,
split_angle,
&lnors_spacearr,
- NULL,
+ nullptr,
loop_to_poly);
/* Set all given zero vectors to their default value. */
@@ -1823,12 +1825,12 @@ static void mesh_normals_loop_custom_set(const MVert *mverts,
for (int i = 0; i < numLoops; i++) {
if (!lnors_spacearr.lspacearr[i]) {
/* This should not happen in theory, but in some rare case (probably ugly geometry)
- * we can get some NULL loopspacearr at this point. :/
+ * we can get some nullptr loopspacearr at this point. :/
* Maybe we should set those loops' edges as sharp?
*/
BLI_BITMAP_ENABLE(done_loops, i);
if (G.debug & G_DEBUG) {
- printf("WARNING! Getting invalid NULL loop space for loop %d!\n", i);
+ printf("WARNING! Getting invalid nullptr loop space for loop %d!\n", i);
}
continue;
}
@@ -1849,8 +1851,8 @@ static void mesh_normals_loop_custom_set(const MVert *mverts,
}
LinkNode *loops = lnors_spacearr.lspacearr[i]->loops;
- MLoop *prev_ml = NULL;
- const float *org_nor = NULL;
+ MLoop *prev_ml = nullptr;
+ const float *org_nor = nullptr;
while (loops) {
const int lidx = POINTER_AS_INT(loops->link);
@@ -1916,7 +1918,7 @@ static void mesh_normals_loop_custom_set(const MVert *mverts,
use_split_normals,
split_angle,
&lnors_spacearr,
- NULL,
+ nullptr,
loop_to_poly);
}
else {
@@ -1929,7 +1931,8 @@ static void mesh_normals_loop_custom_set(const MVert *mverts,
if (!lnors_spacearr.lspacearr[i]) {
BLI_BITMAP_DISABLE(done_loops, i);
if (G.debug & G_DEBUG) {
- printf("WARNING! Still getting invalid NULL loop space in second loop for loop %d!\n", i);
+ printf("WARNING! Still getting invalid nullptr loop space in second loop for loop %d!\n",
+ i);
}
continue;
}
@@ -1970,7 +1973,7 @@ static void mesh_normals_loop_custom_set(const MVert *mverts,
mul_v3_fl(avg_nor, 1.0f / (float)nbr_nors);
BKE_lnor_space_custom_normal_to_data(lnors_spacearr.lspacearr[i], avg_nor, clnor_data_tmp);
- while ((clnor_data = BLI_SMALLSTACK_POP(clnors_data))) {
+ while ((clnor_data = (short *)BLI_SMALLSTACK_POP(clnors_data))) {
clnor_data[0] = clnor_data_tmp[0];
clnor_data[1] = clnor_data_tmp[1];
}
@@ -2041,20 +2044,21 @@ static void mesh_set_custom_normals(Mesh *mesh, float (*r_custom_nors)[3], const
short(*clnors)[2];
const int numloops = mesh->totloop;
- clnors = CustomData_get_layer(&mesh->ldata, CD_CUSTOMLOOPNORMAL);
- if (clnors != NULL) {
+ clnors = (short(*)[2])CustomData_get_layer(&mesh->ldata, CD_CUSTOMLOOPNORMAL);
+ if (clnors != nullptr) {
memset(clnors, 0, sizeof(*clnors) * (size_t)numloops);
}
else {
- clnors = CustomData_add_layer(&mesh->ldata, CD_CUSTOMLOOPNORMAL, CD_CALLOC, NULL, numloops);
+ clnors = (short(*)[2])CustomData_add_layer(
+ &mesh->ldata, CD_CUSTOMLOOPNORMAL, CD_CALLOC, nullptr, numloops);
}
- float(*polynors)[3] = CustomData_get_layer(&mesh->pdata, CD_NORMAL);
+ float(*polynors)[3] = (float(*)[3])CustomData_get_layer(&mesh->pdata, CD_NORMAL);
bool free_polynors = false;
- if (polynors == NULL) {
- polynors = MEM_mallocN(sizeof(float[3]) * (size_t)mesh->totpoly, __func__);
+ if (polynors == nullptr) {
+ polynors = (float(*)[3])MEM_mallocN(sizeof(float[3]) * (size_t)mesh->totpoly, __func__);
BKE_mesh_calc_normals_poly(mesh->mvert,
- NULL,
+ nullptr,
mesh->totvert,
mesh->mloop,
mesh->mpoly,
@@ -2119,7 +2123,8 @@ void BKE_mesh_normals_loop_to_vertex(const int numVerts,
const float (*clnors)[3],
float (*r_vert_clnors)[3])
{
- int *vert_loops_nbr = MEM_calloc_arrayN((size_t)numVerts, sizeof(*vert_loops_nbr), __func__);
+ int *vert_loops_nbr = (int *)MEM_calloc_arrayN(
+ (size_t)numVerts, sizeof(*vert_loops_nbr), __func__);
copy_vn_fl((float *)r_vert_clnors, 3 * numVerts, 0.0f);
diff --git a/source/blender/blenkernel/intern/nla.c b/source/blender/blenkernel/intern/nla.c
index bf18765aa94..7e524da0f53 100644
--- a/source/blender/blenkernel/intern/nla.c
+++ b/source/blender/blenkernel/intern/nla.c
@@ -631,10 +631,10 @@ float BKE_nla_tweakedit_remap(AnimData *adt, float cframe, short mode)
{
NlaStrip *strip;
- /* sanity checks
- * - obviously we've got to have some starting data
- * - when not in tweakmode, the active Action does not have any scaling applied :)
- * - when in tweakmode, if the no-mapping flag is set, do not map
+ /* Sanity checks:
+ * - Obviously we've got to have some starting data.
+ * - When not in tweak-mode, the active Action does not have any scaling applied :)
+ * - When in tweak-mode, if the no-mapping flag is set, do not map.
*/
if ((adt == NULL) || (adt->flag & ADT_NLA_EDIT_ON) == 0 || (adt->flag & ADT_NLA_EDIT_NOMAP)) {
return cframe;
@@ -2089,9 +2089,8 @@ bool BKE_nla_tweakmode_enter(AnimData *adt)
return false;
}
- /* if block is already in tweakmode, just leave, but we should report
- * that this block is in tweakmode (as our returncode)
- */
+ /* If block is already in tweak-mode, just leave, but we should report
+ * that this block is in tweak-mode (as our returncode). */
if (adt->flag & ADT_NLA_EDIT_ON) {
return true;
}
@@ -2111,8 +2110,8 @@ bool BKE_nla_tweakmode_enter(AnimData *adt)
}
}
- /* There are situations where we may have multiple strips selected and we want to enter tweakmode
- * on all of those at once. Usually in those cases,
+ /* There are situations where we may have multiple strips selected and we want to enter
+ * tweak-mode on all of those at once. Usually in those cases,
* it will usually just be a single strip per AnimData.
* In such cases, compromise and take the last selected track and/or last selected strip, T28468.
*/
@@ -2142,7 +2141,7 @@ bool BKE_nla_tweakmode_enter(AnimData *adt)
if (ELEM(NULL, activeTrack, activeStrip, activeStrip->act)) {
if (G.debug & G_DEBUG) {
- printf("NLA tweakmode enter - neither active requirement found\n");
+ printf("NLA tweak-mode enter - neither active requirement found\n");
printf("\tactiveTrack = %p, activeStrip = %p\n", (void *)activeTrack, (void *)activeStrip);
}
return false;
@@ -2192,7 +2191,7 @@ bool BKE_nla_tweakmode_enter(AnimData *adt)
return true;
}
-/* Exit tweakmode for this AnimData block */
+/* Exit tweak-mode for this AnimData block. */
void BKE_nla_tweakmode_exit(AnimData *adt)
{
NlaStrip *strip;
diff --git a/source/blender/blenkernel/intern/node.cc b/source/blender/blenkernel/intern/node.cc
index f6105bac1a8..e4c259ec9fc 100644
--- a/source/blender/blenkernel/intern/node.cc
+++ b/source/blender/blenkernel/intern/node.cc
@@ -69,7 +69,6 @@
#include "BKE_lib_query.h"
#include "BKE_main.h"
#include "BKE_node.h"
-#include "BKE_node_ui_storage.hh"
#include "BLI_ghash.h"
#include "BLI_threads.h"
@@ -220,10 +219,6 @@ static void ntree_copy_data(Main *UNUSED(bmain), ID *id_dst, const ID *id_src, c
/* node tree will generate its own interface type */
ntree_dst->interface_type = nullptr;
-
- /* Don't copy error messages in the runtime struct.
- * They should be filled during execution anyway. */
- ntree_dst->ui_storage = nullptr;
}
static void ntree_free_data(ID *id)
@@ -277,8 +272,6 @@ static void ntree_free_data(ID *id)
if (ntree->id.tag & LIB_TAG_LOCALIZED) {
BKE_libblock_free_data(&ntree->id, true);
}
-
- delete ntree->ui_storage;
}
static void library_foreach_node_socket(LibraryForeachIDData *data, bNodeSocket *sock)
@@ -621,7 +614,6 @@ static void ntree_blend_write(BlendWriter *writer, ID *id, const void *id_addres
ntree->interface_type = nullptr;
ntree->progress = nullptr;
ntree->execdata = nullptr;
- ntree->ui_storage = nullptr;
BLO_write_id_struct(writer, bNodeTree, id_address, &ntree->id);
@@ -653,7 +645,6 @@ void ntreeBlendReadData(BlendDataReader *reader, bNodeTree *ntree)
ntree->progress = nullptr;
ntree->execdata = nullptr;
- ntree->ui_storage = nullptr;
BLO_read_data_address(reader, &ntree->adt);
BKE_animdata_blend_read_data(reader, ntree->adt);
@@ -1425,6 +1416,12 @@ GHashIterator *nodeSocketTypeGetIterator(void)
return BLI_ghashIterator_new(nodesockettypes_hash);
}
+const char *nodeSocketTypeLabel(const bNodeSocketType *stype)
+{
+ /* Use socket type name as a fallback if label is undefined. */
+ return stype->label[0] != '\0' ? stype->label : RNA_struct_ui_name(stype->ext_socket.srna);
+}
+
struct bNodeSocket *nodeFindSocket(const bNode *node,
eNodeSocketInOut in_out,
const char *identifier)
@@ -1585,13 +1582,15 @@ static void socket_id_user_decrement(bNodeSocket *sock)
}
}
-void nodeModifySocketType(
- bNodeTree *ntree, bNode *UNUSED(node), bNodeSocket *sock, int type, int subtype)
+void nodeModifySocketType(bNodeTree *ntree,
+ bNode *UNUSED(node),
+ bNodeSocket *sock,
+ const char *idname)
{
- const char *idname = nodeStaticSocketType(type, subtype);
+ bNodeSocketType *socktype = nodeSocketTypeFind(idname);
- if (!idname) {
- CLOG_ERROR(&LOG, "static node socket type %d undefined", type);
+ if (!socktype) {
+ CLOG_ERROR(&LOG, "node socket type %s undefined", idname);
return;
}
@@ -1601,9 +1600,21 @@ void nodeModifySocketType(
sock->default_value = nullptr;
}
- sock->type = type;
BLI_strncpy(sock->idname, idname, sizeof(sock->idname));
- node_socket_set_typeinfo(ntree, sock, nodeSocketTypeFind(idname));
+ node_socket_set_typeinfo(ntree, sock, socktype);
+}
+
+void nodeModifySocketTypeStatic(
+ bNodeTree *ntree, bNode *node, bNodeSocket *sock, int type, int subtype)
+{
+ const char *idname = nodeStaticSocketType(type, subtype);
+
+ if (!idname) {
+ CLOG_ERROR(&LOG, "static node socket type %d undefined", type);
+ return;
+ }
+
+ nodeModifySocketType(ntree, node, sock, idname);
}
bNodeSocket *nodeAddSocket(bNodeTree *ntree,
@@ -1647,6 +1658,15 @@ bNodeSocket *nodeInsertSocket(bNodeTree *ntree,
return sock;
}
+bool nodeIsStaticSocketType(const struct bNodeSocketType *stype)
+{
+ /*
+ * Cannot rely on type==SOCK_CUSTOM here, because type is 0 by default
+ * and can be changed on custom sockets.
+ */
+ return RNA_struct_is_a(stype->ext_socket.srna, &RNA_NodeSocketStandard);
+}
+
const char *nodeStaticSocketType(int type, int subtype)
{
switch (type) {
@@ -1801,6 +1821,39 @@ const char *nodeStaticSocketInterfaceType(int type, int subtype)
return nullptr;
}
+const char *nodeStaticSocketLabel(int type, int UNUSED(subtype))
+{
+ switch (type) {
+ case SOCK_FLOAT:
+ return "Float";
+ case SOCK_INT:
+ return "Integer";
+ case SOCK_BOOLEAN:
+ return "Boolean";
+ case SOCK_VECTOR:
+ return "Vector";
+ case SOCK_RGBA:
+ return "Color";
+ case SOCK_STRING:
+ return "String";
+ case SOCK_SHADER:
+ return "Shader";
+ case SOCK_OBJECT:
+ return "Object";
+ case SOCK_IMAGE:
+ return "Image";
+ case SOCK_GEOMETRY:
+ return "Geometry";
+ case SOCK_COLLECTION:
+ return "Collection";
+ case SOCK_TEXTURE:
+ return "Texture";
+ case SOCK_MATERIAL:
+ return "Material";
+ }
+ return nullptr;
+}
+
bNodeSocket *nodeAddStaticSocket(bNodeTree *ntree,
bNode *node,
eNodeSocketInOut in_out,
@@ -5044,27 +5097,29 @@ static void registerGeometryNodes()
register_node_type_geo_attribute_mix();
register_node_type_geo_attribute_proximity();
register_node_type_geo_attribute_randomize();
+ register_node_type_geo_attribute_remove();
register_node_type_geo_attribute_separate_xyz();
register_node_type_geo_attribute_transfer();
register_node_type_geo_attribute_vector_math();
register_node_type_geo_attribute_vector_rotate();
- register_node_type_geo_attribute_remove();
register_node_type_geo_boolean();
register_node_type_geo_bounding_box();
register_node_type_geo_collection_info();
register_node_type_geo_convex_hull();
+ register_node_type_geo_curve_endpoints();
register_node_type_geo_curve_length();
register_node_type_geo_curve_primitive_bezier_segment();
register_node_type_geo_curve_primitive_circle();
register_node_type_geo_curve_primitive_line();
register_node_type_geo_curve_primitive_quadratic_bezier();
+ register_node_type_geo_curve_primitive_quadrilateral();
register_node_type_geo_curve_primitive_spiral();
register_node_type_geo_curve_primitive_star();
- register_node_type_geo_curve_to_mesh();
- register_node_type_geo_curve_to_points();
register_node_type_geo_curve_resample();
register_node_type_geo_curve_reverse();
register_node_type_geo_curve_subdivide();
+ register_node_type_geo_curve_to_mesh();
+ register_node_type_geo_curve_to_points();
register_node_type_geo_delete_geometry();
register_node_type_geo_edge_split();
register_node_type_geo_input_material();
@@ -5080,6 +5135,7 @@ static void registerGeometryNodes()
register_node_type_geo_mesh_primitive_ico_sphere();
register_node_type_geo_mesh_primitive_line();
register_node_type_geo_mesh_primitive_uv_sphere();
+ register_node_type_geo_mesh_subdivide();
register_node_type_geo_mesh_to_curve();
register_node_type_geo_object_info();
register_node_type_geo_point_distribute();
@@ -5093,7 +5149,6 @@ static void registerGeometryNodes()
register_node_type_geo_sample_texture();
register_node_type_geo_select_by_material();
register_node_type_geo_separate_components();
- register_node_type_geo_subdivide();
register_node_type_geo_subdivision_surface();
register_node_type_geo_switch();
register_node_type_geo_transform();
diff --git a/source/blender/blenkernel/intern/node_ui_storage.cc b/source/blender/blenkernel/intern/node_ui_storage.cc
deleted file mode 100644
index e5e9f00c7c3..00000000000
--- a/source/blender/blenkernel/intern/node_ui_storage.cc
+++ /dev/null
@@ -1,169 +0,0 @@
-/*
- * This program is free software; you can redistribute it and/or
- * modify it under the terms of the GNU General Public License
- * as published by the Free Software Foundation; either version 2
- * of the License, or (at your option) any later version.
- *
- * This program is distributed in the hope that it will be useful,
- * but WITHOUT ANY WARRANTY; without even the implied warranty of
- * MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the
- * GNU General Public License for more details.
- *
- * You should have received a copy of the GNU General Public License
- * along with this program; if not, write to the Free Software Foundation,
- * Inc., 51 Franklin Street, Fifth Floor, Boston, MA 02110-1301, USA.
- */
-
-#include "CLG_log.h"
-
-#include <mutex>
-
-#include "BLI_map.hh"
-#include "BLI_string_ref.hh"
-#include "BLI_vector.hh"
-
-#include "DNA_node_types.h"
-#include "DNA_object_types.h"
-
-#include "BKE_context.h"
-#include "BKE_node_ui_storage.hh"
-#include "BKE_object.h"
-
-static CLG_LogRef LOG = {"bke.node_ui_storage"};
-
-using blender::Map;
-using blender::StringRef;
-using blender::Vector;
-
-/* Use a global mutex because otherwise it would have to be stored directly in the
- * bNodeTree struct in DNA. This could change if the node tree had a runtime struct. */
-static std::mutex global_ui_storage_mutex;
-
-static NodeTreeUIStorage &ui_storage_ensure(bNodeTree &ntree)
-{
- /* As an optimization, only acquire a lock if the UI storage doesn't exist,
- * because it only needs to be allocated once for every node tree. */
- if (ntree.ui_storage == nullptr) {
- std::lock_guard<std::mutex> lock(global_ui_storage_mutex);
- /* Check again-- another thread may have allocated the storage while this one waited. */
- if (ntree.ui_storage == nullptr) {
- ntree.ui_storage = new NodeTreeUIStorage();
- }
- }
- return *ntree.ui_storage;
-}
-
-const NodeUIStorage *BKE_node_tree_ui_storage_get_from_context(const bContext *C,
- const bNodeTree &ntree,
- const bNode &node)
-{
- const NodeTreeUIStorage *ui_storage = ntree.ui_storage;
- if (ui_storage == nullptr) {
- return nullptr;
- }
-
- const Object *active_object = CTX_data_active_object(C);
- if (active_object == nullptr) {
- return nullptr;
- }
-
- const ModifierData *active_modifier = BKE_object_active_modifier(active_object);
- if (active_modifier == nullptr) {
- return nullptr;
- }
-
- const NodeTreeEvaluationContext context(*active_object, *active_modifier);
- const Map<std::string, NodeUIStorage> *storage = ui_storage->context_map.lookup_ptr(context);
- if (storage == nullptr) {
- return nullptr;
- }
-
- return storage->lookup_ptr_as(StringRef(node.name));
-}
-
-/**
- * Removes only the UI data associated with a particular evaluation context. The same node tree
- * can be used for execution in multiple places, but the entire UI storage can't be removed when
- * one execution starts, or all of the data associated with the node tree would be lost.
- */
-void BKE_nodetree_ui_storage_free_for_context(bNodeTree &ntree,
- const NodeTreeEvaluationContext &context)
-{
- NodeTreeUIStorage *ui_storage = ntree.ui_storage;
- if (ui_storage != nullptr) {
- std::lock_guard<std::mutex> lock(ui_storage->mutex);
- ui_storage->context_map.remove(context);
- }
-}
-
-static void node_error_message_log(bNodeTree &ntree,
- const bNode &node,
- const StringRef message,
- const NodeWarningType type)
-{
- switch (type) {
- case NodeWarningType::Error:
- CLOG_ERROR(&LOG,
- "Node Tree: \"%s\", Node: \"%s\", %s",
- ntree.id.name + 2,
- node.name,
- message.data());
- break;
- case NodeWarningType::Warning:
- CLOG_WARN(&LOG,
- "Node Tree: \"%s\", Node: \"%s\", %s",
- ntree.id.name + 2,
- node.name,
- message.data());
- break;
- case NodeWarningType::Info:
- CLOG_INFO(&LOG,
- 2,
- "Node Tree: \"%s\", Node: \"%s\", %s",
- ntree.id.name + 2,
- node.name,
- message.data());
- break;
- }
-}
-
-static NodeUIStorage &node_ui_storage_ensure(NodeTreeUIStorage &locked_ui_storage,
- const NodeTreeEvaluationContext &context,
- const bNode &node)
-{
- Map<std::string, NodeUIStorage> &node_tree_ui_storage =
- locked_ui_storage.context_map.lookup_or_add_default(context);
- NodeUIStorage &node_ui_storage = node_tree_ui_storage.lookup_or_add_default_as(
- StringRef(node.name));
- return node_ui_storage;
-}
-
-void BKE_nodetree_error_message_add(bNodeTree &ntree,
- const NodeTreeEvaluationContext &context,
- const bNode &node,
- const NodeWarningType type,
- std::string message)
-{
- NodeTreeUIStorage &ui_storage = ui_storage_ensure(ntree);
- std::lock_guard lock{ui_storage.mutex};
-
- node_error_message_log(ntree, node, message, type);
-
- NodeUIStorage &node_ui_storage = node_ui_storage_ensure(ui_storage, context, node);
- node_ui_storage.warnings.append({type, std::move(message)});
-}
-
-void BKE_nodetree_attribute_hint_add(bNodeTree &ntree,
- const NodeTreeEvaluationContext &context,
- const bNode &node,
- const StringRef attribute_name,
- const AttributeDomain domain,
- const CustomDataType data_type)
-{
- NodeTreeUIStorage &ui_storage = ui_storage_ensure(ntree);
- std::lock_guard lock{ui_storage.mutex};
-
- NodeUIStorage &node_ui_storage = node_ui_storage_ensure(ui_storage, context, node);
- node_ui_storage.attribute_hints.add_as(
- AvailableAttributeInfo{attribute_name, domain, data_type});
-}
diff --git a/source/blender/blenkernel/intern/object.c b/source/blender/blenkernel/intern/object.c
index a13feafb70b..912b5e0a0dd 100644
--- a/source/blender/blenkernel/intern/object.c
+++ b/source/blender/blenkernel/intern/object.c
@@ -1753,10 +1753,6 @@ void BKE_object_free_derived_caches(Object *ob)
BKE_geometry_set_free(ob->runtime.geometry_set_eval);
ob->runtime.geometry_set_eval = NULL;
}
- if (ob->runtime.geometry_set_previews != NULL) {
- BLI_ghash_free(ob->runtime.geometry_set_previews, NULL, (GHashValFreeFP)BKE_geometry_set_free);
- ob->runtime.geometry_set_previews = NULL;
- }
}
void BKE_object_free_caches(Object *object)
@@ -1807,24 +1803,6 @@ void BKE_object_free_caches(Object *object)
}
}
-/* Can be called from multiple threads. */
-void BKE_object_preview_geometry_set_add(Object *ob,
- const uint64_t key,
- struct GeometrySet *geometry_set)
-{
- static ThreadMutex mutex = BLI_MUTEX_INITIALIZER;
- BLI_mutex_lock(&mutex);
- if (ob->runtime.geometry_set_previews == NULL) {
- ob->runtime.geometry_set_previews = BLI_ghash_int_new(__func__);
- }
- BLI_ghash_reinsert(ob->runtime.geometry_set_previews,
- POINTER_FROM_UINT(key),
- geometry_set,
- NULL,
- (GHashValFreeFP)BKE_geometry_set_free);
- BLI_mutex_unlock(&mutex);
-}
-
/**
* Actual check for internal data, not context or flags.
*/
@@ -2828,7 +2806,7 @@ void BKE_object_copy_proxy_drivers(Object *ob, Object *target)
/* add new animdata block */
if (!ob->adt) {
- ob->adt = BKE_animdata_add_id(&ob->id);
+ ob->adt = BKE_animdata_ensure_id(&ob->id);
}
/* make a copy of all the drivers (for now), then correct any links that need fixing */
@@ -4155,6 +4133,30 @@ bool BKE_object_minmax_dupli(Depsgraph *depsgraph,
return ok;
}
+struct GPencilStrokePointIterData {
+ const float (*obmat)[4];
+
+ void (*point_func_cb)(const float co[3], void *user_data);
+ void *user_data;
+};
+
+static void foreach_display_point_gpencil_stroke_fn(bGPDlayer *UNUSED(layer),
+ bGPDframe *UNUSED(frame),
+ bGPDstroke *stroke,
+ void *thunk)
+{
+ struct GPencilStrokePointIterData *iter_data = thunk;
+ {
+ bGPDspoint *pt;
+ int i;
+ for (i = 0, pt = stroke->points; i < stroke->totpoints; i++, pt++) {
+ float co[3];
+ mul_v3_m4v3(co, iter_data->obmat, &pt->x);
+ iter_data->point_func_cb(co, iter_data->user_data);
+ }
+ }
+}
+
void BKE_object_foreach_display_point(Object *ob,
const float obmat[4][4],
void (*func_cb)(const float[3], void *),
@@ -4172,6 +4174,13 @@ void BKE_object_foreach_display_point(Object *ob,
func_cb(co, user_data);
}
}
+ else if (ob->type == OB_GPENCIL) {
+ struct GPencilStrokePointIterData iter_data = {
+ .obmat = obmat, .point_func_cb = func_cb, .user_data = user_data};
+
+ BKE_gpencil_visible_stroke_iter(
+ ob->data, NULL, foreach_display_point_gpencil_stroke_fn, &iter_data);
+ }
else if (ob->runtime.curve_cache && ob->runtime.curve_cache->disp.first) {
DispList *dl;
diff --git a/source/blender/blenkernel/intern/object_update.c b/source/blender/blenkernel/intern/object_update.c
index ab247ef5507..7cdea14e9bd 100644
--- a/source/blender/blenkernel/intern/object_update.c
+++ b/source/blender/blenkernel/intern/object_update.c
@@ -123,7 +123,7 @@ void BKE_object_eval_parent(Depsgraph *depsgraph, Object *ob)
void BKE_object_eval_constraints(Depsgraph *depsgraph, Scene *scene, Object *ob)
{
bConstraintOb *cob;
- float ctime = BKE_scene_frame_get(scene);
+ float ctime = BKE_scene_ctime_get(scene);
DEG_debug_print_eval(depsgraph, __func__, ob->id.name, ob);
@@ -388,12 +388,31 @@ void BKE_object_batch_cache_dirty_tag(Object *ob)
BKE_object_data_batch_cache_dirty_tag(ob->data);
}
+void BKE_object_data_eval_batch_cache_dirty_tag(Depsgraph *depsgraph, ID *object_data)
+{
+ DEG_debug_print_eval(depsgraph, __func__, object_data->name, object_data);
+ BKE_object_data_batch_cache_dirty_tag(object_data);
+}
+
+void BKE_object_data_eval_batch_cache_deform_tag(Depsgraph *depsgraph, ID *object_data)
+{
+ DEG_debug_print_eval(depsgraph, __func__, object_data->name, object_data);
+ switch (GS(object_data->name)) {
+ case ID_ME:
+ BKE_mesh_batch_cache_dirty_tag((Mesh *)object_data, BKE_MESH_BATCH_DIRTY_DEFORM);
+ break;
+ default:
+ /* Only mesh is currently supported. Fallback to dirty all for other datablocks types. */
+ BKE_object_data_batch_cache_dirty_tag(object_data);
+ break;
+ }
+}
+
void BKE_object_eval_uber_data(Depsgraph *depsgraph, Scene *scene, Object *ob)
{
DEG_debug_print_eval(depsgraph, __func__, ob->id.name, ob);
BLI_assert(ob->type != OB_ARMATURE);
BKE_object_handle_data_update(depsgraph, scene, ob);
- BKE_object_batch_cache_dirty_tag(ob);
}
void BKE_object_eval_ptcache_reset(Depsgraph *depsgraph, Scene *scene, Object *object)
diff --git a/source/blender/blenkernel/intern/particle.c b/source/blender/blenkernel/intern/particle.c
index 7504fbeed19..db1fbb56125 100644
--- a/source/blender/blenkernel/intern/particle.c
+++ b/source/blender/blenkernel/intern/particle.c
@@ -3961,7 +3961,7 @@ static ModifierData *object_add_or_copy_particle_system(
psys->totpart = 0;
psys->flag = PSYS_CURRENT;
if (scene != NULL) {
- psys->cfra = BKE_scene_frame_to_ctime(scene, CFRA + 1);
+ psys->cfra = BKE_scene_frame_to_ctime(scene, scene->r.cfra + 1);
}
DEG_relations_tag_update(bmain);
diff --git a/source/blender/blenkernel/intern/pbvh.c b/source/blender/blenkernel/intern/pbvh.c
index 18b4c72932d..1f8f9ce63ac 100644
--- a/source/blender/blenkernel/intern/pbvh.c
+++ b/source/blender/blenkernel/intern/pbvh.c
@@ -2157,7 +2157,7 @@ static bool pbvh_faces_node_raycast(PBVH *pbvh,
const float *co[3];
if (origco) {
- /* intersect with backuped original coordinates */
+ /* Intersect with backed up original coordinates. */
co[0] = origco[face_verts[0]];
co[1] = origco[face_verts[1]];
co[2] = origco[face_verts[2]];
diff --git a/source/blender/blenkernel/intern/pointcache.c b/source/blender/blenkernel/intern/pointcache.c
index 90018e64f78..9ed5b0230e6 100644
--- a/source/blender/blenkernel/intern/pointcache.c
+++ b/source/blender/blenkernel/intern/pointcache.c
@@ -2807,8 +2807,8 @@ void BKE_ptcache_id_time(
cache = pid->cache;
if (timescale) {
- time = BKE_scene_frame_get(scene);
- nexttime = BKE_scene_frame_to_ctime(scene, CFRA + 1.0f);
+ time = BKE_scene_ctime_get(scene);
+ nexttime = BKE_scene_frame_to_ctime(scene, scene->r.cfra + 1);
*timescale = MAX2(nexttime - time, 0.0f);
}
diff --git a/source/blender/blenkernel/intern/scene.c b/source/blender/blenkernel/intern/scene.c
index f8f4d52fcf2..cc5a8536a5a 100644
--- a/source/blender/blenkernel/intern/scene.c
+++ b/source/blender/blenkernel/intern/scene.c
@@ -2299,10 +2299,7 @@ Object *BKE_scene_camera_switch_find(Scene *scene)
return NULL;
}
- const int cfra = ((scene->r.images == scene->r.framapto) ?
- scene->r.cfra :
- (int)(scene->r.cfra *
- ((float)scene->r.framapto / (float)scene->r.images)));
+ const int ctime = (int)BKE_scene_ctime_get(scene);
int frame = -(MAXFRAME + 1);
int min_frame = MAXFRAME + 1;
Object *camera = NULL;
@@ -2310,11 +2307,11 @@ Object *BKE_scene_camera_switch_find(Scene *scene)
LISTBASE_FOREACH (TimeMarker *, m, &scene->markers) {
if (m->camera && (m->camera->restrictflag & OB_RESTRICT_RENDER) == 0) {
- if ((m->frame <= cfra) && (m->frame > frame)) {
+ if ((m->frame <= ctime) && (m->frame > frame)) {
camera = m->camera;
frame = m->frame;
- if (frame == cfra) {
+ if (frame == ctime) {
break;
}
}
@@ -2396,13 +2393,13 @@ const char *BKE_scene_find_last_marker_name(const Scene *scene, int frame)
return best_marker ? best_marker->name : NULL;
}
-int BKE_scene_frame_snap_by_seconds(Scene *scene, double interval_in_seconds, int cfra)
+int BKE_scene_frame_snap_by_seconds(Scene *scene, double interval_in_seconds, int frame)
{
const int fps = round_db_to_int(FPS * interval_in_seconds);
- const int second_prev = cfra - mod_i(cfra, fps);
+ const int second_prev = frame - mod_i(frame, fps);
const int second_next = second_prev + fps;
- const int delta_prev = cfra - second_prev;
- const int delta_next = second_next - cfra;
+ const int delta_prev = frame - second_prev;
+ const int delta_next = second_next - frame;
return (delta_prev < delta_next) ? second_prev : second_next;
}
@@ -2444,16 +2441,17 @@ bool BKE_scene_validate_setscene(Main *bmain, Scene *sce)
return true;
}
-/**
- * This function is needed to cope with fractional frames, needed for motion blur & physics.
- */
-float BKE_scene_frame_get(const Scene *scene)
+/* Return fractional frame number taking into account subframes and time
+ * remapping. This the time value used by animation, modifiers and physics
+ * evaluation. */
+float BKE_scene_ctime_get(const Scene *scene)
{
return BKE_scene_frame_to_ctime(scene, scene->r.cfra);
}
-/* This function is used to obtain arbitrary fractional frames */
-float BKE_scene_frame_to_ctime(const Scene *scene, const float frame)
+/* Convert integer frame number to fractional frame number taking into account
+ * subframes and time remapping. */
+float BKE_scene_frame_to_ctime(const Scene *scene, const int frame)
{
float ctime = frame;
ctime += scene->r.subframe;
@@ -2461,13 +2459,18 @@ float BKE_scene_frame_to_ctime(const Scene *scene, const float frame)
return ctime;
}
-/**
- * Sets the frame int/float components.
- */
-void BKE_scene_frame_set(struct Scene *scene, double cfra)
+
+/* Get current fractional frame based on frame and subframe. */
+float BKE_scene_frame_get(const Scene *scene)
+{
+ return scene->r.cfra + scene->r.subframe;
+}
+
+/* Set current frame and subframe based on a fractional frame. */
+void BKE_scene_frame_set(Scene *scene, float frame)
{
double intpart;
- scene->r.subframe = modf(cfra, &intpart);
+ scene->r.subframe = modf((double)frame, &intpart);
scene->r.cfra = (int)intpart;
}
@@ -2736,8 +2739,8 @@ void BKE_scene_graph_update_for_newframe_ex(Depsgraph *depsgraph, const bool cle
* edits from callback are properly taken into account. Doing a time update on those would
* lose any possible unkeyed changes made by the handler. */
if (pass == 0) {
- const float ctime = BKE_scene_frame_get(scene);
- DEG_evaluate_on_framechange(depsgraph, ctime);
+ const float frame = BKE_scene_frame_get(scene);
+ DEG_evaluate_on_framechange(depsgraph, frame);
}
else {
DEG_evaluate_on_refresh(depsgraph);
diff --git a/source/blender/blenkernel/intern/screen.c b/source/blender/blenkernel/intern/screen.c
index a2809543b95..73658c3184e 100644
--- a/source/blender/blenkernel/intern/screen.c
+++ b/source/blender/blenkernel/intern/screen.c
@@ -1734,6 +1734,12 @@ static void direct_link_area(BlendDataReader *reader, ScrArea *area)
sfile->runtime = NULL;
BLO_read_data_address(reader, &sfile->params);
BLO_read_data_address(reader, &sfile->asset_params);
+ if (sfile->params) {
+ sfile->params->rename_id = NULL;
+ }
+ if (sfile->asset_params) {
+ sfile->asset_params->base_params.rename_id = NULL;
+ }
}
else if (sl->spacetype == SPACE_ACTION) {
SpaceAction *saction = (SpaceAction *)sl;
diff --git a/source/blender/blenkernel/intern/softbody.c b/source/blender/blenkernel/intern/softbody.c
index f978e5e8de4..e4e2ed94b41 100644
--- a/source/blender/blenkernel/intern/softbody.c
+++ b/source/blender/blenkernel/intern/softbody.c
@@ -3086,7 +3086,7 @@ static void softbody_to_object(Object *ob, float (*vertexCos)[3], int numVerts,
if (sb->solverflags & SBSO_ESTIMATEIPO) {
SB_estimate_transform(ob, sb->lcom, sb->lrot, sb->lscale);
}
- /* inverse matrix is not uptodate... */
+ /* Inverse matrix is not up to date. */
invert_m4_m4(ob->imat, ob->obmat);
for (a = 0; a < numVerts; a++, bp++) {
diff --git a/source/blender/blenkernel/intern/spline_base.cc b/source/blender/blenkernel/intern/spline_base.cc
index aa0d95d4d61..6234cdf87e2 100644
--- a/source/blender/blenkernel/intern/spline_base.cc
+++ b/source/blender/blenkernel/intern/spline_base.cc
@@ -512,6 +512,10 @@ void Spline::sample_with_index_factors(const GVArray &src,
using T = decltype(dummy);
const GVArray_Typed<T> src_typed = src.typed<T>();
MutableSpan<T> dst_typed = dst.typed<T>();
+ if (src.size() == 1) {
+ dst_typed.fill(src_typed[0]);
+ return;
+ }
blender::threading::parallel_for(dst_typed.index_range(), 1024, [&](IndexRange range) {
for (const int i : range) {
const LookupResult interp = this->lookup_data_from_index_factor(index_factors[i]);
diff --git a/source/blender/blenkernel/intern/spline_nurbs.cc b/source/blender/blenkernel/intern/spline_nurbs.cc
index 76d046337c0..ac6f1bd082c 100644
--- a/source/blender/blenkernel/intern/spline_nurbs.cc
+++ b/source/blender/blenkernel/intern/spline_nurbs.cc
@@ -346,7 +346,10 @@ Span<NURBSpline::BasisCache> NURBSpline::calculate_basis_cache() const
const int size = this->size();
const int eval_size = this->evaluated_points_size();
- BLI_assert(this->evaluated_edges_size() > 0);
+ if (eval_size == 0) {
+ return {};
+ }
+
basis_cache_.resize(eval_size);
const int order = this->order();
diff --git a/source/blender/blenkernel/intern/studiolight.c b/source/blender/blenkernel/intern/studiolight.c
index 4cc2d101b02..dc5162f201e 100644
--- a/source/blender/blenkernel/intern/studiolight.c
+++ b/source/blender/blenkernel/intern/studiolight.c
@@ -1352,7 +1352,7 @@ static void studiolight_irradiance_preview(uint *icon_buffer, StudioLight *sl)
ITER_PIXELS_END;
}
-void BKE_studiolight_default(SolidLight lights[4], float light_ambient[4])
+void BKE_studiolight_default(SolidLight lights[4], float light_ambient[3])
{
copy_v3_fl3(light_ambient, 0.0, 0.0, 0.0);
diff --git a/source/blender/blenkernel/intern/tracking_region_tracker.c b/source/blender/blenkernel/intern/tracking_region_tracker.c
index ef36acdc3d5..179def0a6f2 100644
--- a/source/blender/blenkernel/intern/tracking_region_tracker.c
+++ b/source/blender/blenkernel/intern/tracking_region_tracker.c
@@ -155,7 +155,7 @@ static ImBuf *tracking_context_get_keyframed_ibuf(MovieClip *clip,
return tracking_context_get_frame_ibuf(clip, user, clip_flag, keyed_framenr);
}
-/* Get image buffer which si used as reference for track. */
+/* Get image buffer which is used as reference for track. */
static ImBuf *tracking_context_get_reference_ibuf(MovieClip *clip,
MovieClipUser *user,
int clip_flag,
diff --git a/source/blender/blenkernel/intern/undo_system.c b/source/blender/blenkernel/intern/undo_system.c
index fe2aa701c63..03bd9323f39 100644
--- a/source/blender/blenkernel/intern/undo_system.c
+++ b/source/blender/blenkernel/intern/undo_system.c
@@ -722,6 +722,24 @@ eUndoStepDir BKE_undosys_step_calc_direction(const UndoStack *ustack,
}
/**
+ * When reading undo steps for undo/redo,
+ * some extra checks are needed when so the correct undo step is decoded.
+ */
+static UndoStep *undosys_step_iter_first(UndoStep *us_reference, const eUndoStepDir undo_dir)
+{
+ if (us_reference->type->flags & UNDOTYPE_FLAG_DECODE_ACTIVE_STEP) {
+ /* Reading this step means an undo action reads undo twice.
+ * This should be avoided where possible, however some undo systems require it.
+ *
+ * Redo skips the current state as this represents the currently loaded state. */
+ return (undo_dir == -1) ? us_reference : us_reference->next;
+ }
+
+ /* Typical case, skip reading the current undo step. */
+ return (undo_dir == -1) ? us_reference->prev : us_reference->next;
+}
+
+/**
* Undo/Redo until the given `us_target` step becomes the active (currently loaded) one.
*
* \note Unless `us_target` is a 'skipped' one and `use_skip` is true, `us_target` will become the
@@ -786,15 +804,10 @@ bool BKE_undosys_step_load_data_ex(UndoStack *ustack,
us_target->type->name,
undo_dir);
- /* Undo/Redo steps until we reach given target step (or beyond if it has to be skipped), from
- * given reference step.
- *
- * NOTE: Unlike with redo case, where we can expect current active step to fully reflect current
- * data status, in undo case we also do reload the active step.
- * FIXME: this feels weak, and should probably not be actually needed? Or should also be done in
- * redo case? */
+ /* Undo/Redo steps until we reach given target step (or beyond if it has to be skipped),
+ * from given reference step. */
bool is_processing_extra_skipped_steps = false;
- for (UndoStep *us_iter = (undo_dir == -1) ? us_reference : us_reference->next; us_iter != NULL;
+ for (UndoStep *us_iter = undosys_step_iter_first(us_reference, undo_dir); us_iter != NULL;
us_iter = (undo_dir == -1) ? us_iter->prev : us_iter->next) {
BLI_assert(us_iter != NULL);