[Bf-blender-cvs] [faf8402c190] temp_bmesh_multires: Added initial support for customdata to dyntopo undo (BMLog).
Joseph Eagar
noreply at git.blender.org
Mon Oct 26 10:47:20 CET 2020
Commit: faf8402c190d1af34b08fdd89561854095b612ee
Author: Joseph Eagar
Date: Mon Oct 26 02:45:56 2020 -0700
Branches: temp_bmesh_multires
https://developer.blender.org/rBfaf8402c190d1af34b08fdd89561854095b612ee
Added initial support for customdata to dyntopo undo (BMLog).
TODO:
- Handle face (loop) data
- Figure out what to do about edge data (warn user? actually handle
it?)
- Handle sculpt color undo push nodes properly (shouldn't be hard).
===================================================================
M source/blender/blenkernel/BKE_customdata.h
M source/blender/blenkernel/intern/customdata.c
M source/blender/blenkernel/intern/paint.c
M source/blender/blenkernel/intern/pbvh.c
M source/blender/blenkernel/intern/pbvh_bmesh.c
M source/blender/bmesh/intern/bmesh_log.c
M source/blender/bmesh/intern/bmesh_log.h
M source/blender/editors/sculpt_paint/sculpt.c
M source/blender/editors/sculpt_paint/sculpt_undo.c
===================================================================
diff --git a/source/blender/blenkernel/BKE_customdata.h b/source/blender/blenkernel/BKE_customdata.h
index 51650d161ea..8ac7b625805 100644
--- a/source/blender/blenkernel/BKE_customdata.h
+++ b/source/blender/blenkernel/BKE_customdata.h
@@ -104,6 +104,8 @@ bool CustomData_has_math(const struct CustomData *data);
bool CustomData_has_interp(const struct CustomData *data);
bool CustomData_bmesh_has_free(const struct CustomData *data);
+bool CustomData_layout_is_same(const struct CustomData *_a, const struct CustomData *_b);
+
/**
* Checks if any of the customdata layers is referenced.
*/
@@ -140,6 +142,10 @@ void CustomData_copy(const struct CustomData *source,
/* BMESH_TODO, not really a public function but readfile.c needs it */
void CustomData_update_typemap(struct CustomData *data);
+/* copies all customdata layers without allocating data,
+ * and without respect to type masks or NO_COPY/etc flags*/
+void CustomData_copy_all_layout(const struct CustomData *source, struct CustomData *dest);
+
/* same as the above, except that this will preserve existing layers, and only
* add the layers that were not there yet */
bool CustomData_merge(const struct CustomData *source,
diff --git a/source/blender/blenkernel/intern/customdata.c b/source/blender/blenkernel/intern/customdata.c
index 466a0115a9d..a047cee3168 100644
--- a/source/blender/blenkernel/intern/customdata.c
+++ b/source/blender/blenkernel/intern/customdata.c
@@ -72,6 +72,32 @@ BLI_STATIC_ASSERT(ARRAY_SIZE(((CustomData *)NULL)->typemap) == CD_NUMTYPES, "siz
static CLG_LogRef LOG = {"bke.customdata"};
+bool CustomData_layout_is_same(const CustomData *_a, const CustomData *_b)
+{
+ CustomData a = *_a;
+ CustomData b = *_b;
+
+ a.layers = b.layers = NULL;
+ a.pool = b.pool = NULL;
+
+ if (memcmp((void *)&a, (void *)&b, sizeof(CustomData)) != 0) {
+ return false;
+ }
+
+ for (int i = 0; i < a.totlayer; i++) {
+ CustomDataLayer cla = _a->layers[i];
+ CustomDataLayer clb = _b->layers[i];
+
+ cla.data = clb.data = NULL;
+
+ if (memcmp((void *)&cla, (void *)&clb, sizeof(CustomDataLayer)) != 0) {
+ return false;
+ }
+ }
+
+ return true;
+}
+
/** Update mask_dst with layers defined in mask_src (equivalent to a bitwise OR). */
void CustomData_MeshMasks_update(CustomData_MeshMasks *mask_dst,
const CustomData_MeshMasks *mask_src)
@@ -2072,6 +2098,26 @@ static bool customdata_typemap_is_valid(const CustomData *data)
}
#endif
+/* copies all customdata layers without allocating data,
+ * and without respect to type masks or NO_COPY/etc flags*/
+void CustomData_copy_all_layout(const struct CustomData *source, struct CustomData *dest)
+{
+ *dest = *source;
+
+ if (dest->pool) {
+ dest->pool = NULL;
+ }
+
+ if (source->layers) {
+ dest->layers = MEM_mallocN(sizeof(*dest->layers) * source->totlayer, __func__);
+
+ for (int i = 0; i < source->totlayer; i++) {
+ dest->layers[i] = source->layers[i];
+ dest->layers[i].data = NULL;
+ }
+ }
+}
+
bool CustomData_merge(const struct CustomData *source,
struct CustomData *dest,
CustomDataMask mask,
diff --git a/source/blender/blenkernel/intern/paint.c b/source/blender/blenkernel/intern/paint.c
index 80fe1d659ed..8a40bde0a7e 100644
--- a/source/blender/blenkernel/intern/paint.c
+++ b/source/blender/blenkernel/intern/paint.c
@@ -2048,6 +2048,9 @@ static PBVH *build_pbvh_from_ccg(Object *ob, SubdivCCG *subdiv_ccg, bool respect
return pbvh;
}
+//XXX hack
+extern SCULPT_dynamic_topology_sync_layers(Object *ob, Mesh *me);
+
PBVH *BKE_sculpt_object_pbvh_ensure(Depsgraph *depsgraph, Object *ob)
{
if (ob == NULL || ob->sculpt == NULL) {
diff --git a/source/blender/blenkernel/intern/pbvh.c b/source/blender/blenkernel/intern/pbvh.c
index 31f945262bd..936205c91ce 100644
--- a/source/blender/blenkernel/intern/pbvh.c
+++ b/source/blender/blenkernel/intern/pbvh.c
@@ -1362,11 +1362,17 @@ static void pbvh_update_draw_buffers(PBVH *pbvh, PBVHNode **nodes, int totnode,
CustomData *ldata;
if (pbvh->type == PBVH_BMESH) {
- vdata = &pbvh->bm->vdata;
- ldata = &pbvh->bm->ldata;
- } else {
- vdata = &pbvh->vdata;
- ldata = &pbvh->ldata;
+ if (pbvh->bm) {
+ vdata = &pbvh->bm->vdata;
+ ldata = &pbvh->bm->ldata;
+ }
+ else {
+ vdata = ldata = NULL;
+ }
+ }
+ else {
+ vdata = pbvh->vdata;
+ ldata = pbvh->ldata;
}
GPU_pbvh_update_attribute_names(vdata, ldata);
diff --git a/source/blender/blenkernel/intern/pbvh_bmesh.c b/source/blender/blenkernel/intern/pbvh_bmesh.c
index f45eb2e0a53..611ba8ec2a1 100644
--- a/source/blender/blenkernel/intern/pbvh_bmesh.c
+++ b/source/blender/blenkernel/intern/pbvh_bmesh.c
@@ -1762,7 +1762,10 @@ static void pbvh_bmesh_collapse_edge(PBVH *pbvh,
/* Move v_conn to the midpoint of v_conn and v_del (if v_conn still exists, it
* may have been deleted above) */
if (v_conn != NULL) {
- BM_log_vert_before_modified(pbvh->bm_log, v_conn, eq_ctx->cd_vert_mask_offset);
+ //BM_log_vert_before_modified(pbvh->bm, pbvh->bm_log, v_conn, eq_ctx->cd_vert_mask_offset, false);
+ void *dummy;
+ BKE_pbvh_bmesh_update_origvert(pbvh, v_conn, &dummy, &dummy, &dummy);
+
mid_v3_v3v3(v_conn->co, v_conn->co, v_del->co);
add_v3_v3(v_conn->no, v_del->no);
normalize_v3(v_conn->no);
diff --git a/source/blender/bmesh/intern/bmesh_log.c b/source/blender/bmesh/intern/bmesh_log.c
index aeaa2eb646a..1273a2e40df 100644
--- a/source/blender/bmesh/intern/bmesh_log.c
+++ b/source/blender/bmesh/intern/bmesh_log.c
@@ -1,3 +1,4 @@
+
/*
* This program is free software; you can redistribute it and/or
* modify it under the terms of the GNU General Public License
@@ -45,6 +46,8 @@
#include "BLI_strict_flags.h"
+#define CUSTOMDATA
+
struct BMLogEntry {
struct BMLogEntry *next, *prev;
@@ -75,6 +78,9 @@ struct BMLogEntry {
* This field is not guaranteed to be valid, any use of it should
* check for NULL. */
BMLog *log;
+
+ CustomData vdata, edata, ldata, pdata;
+ struct BMLogEntry *combined_prev, *combined_next;
};
struct BMLog {
@@ -93,6 +99,8 @@ struct BMLog {
GHash *id_to_elem;
GHash *elem_to_id;
+ BMesh *bm;
+
/* All BMLogEntrys, ordered from earliest to most recent */
ListBase entries;
@@ -177,6 +185,51 @@ static BMFace *bm_log_face_from_id(BMLog *log, uint id)
/************************ BMLogVert / BMLogFace ***********************/
+static void bm_log_vert_customdata(BMesh *bm, BMLog *log, BMVert *v, BMLogVert *lv)
+{
+#ifdef CUSTOMDATA
+ // if (!lv) {
+ // return;
+ //}
+ BMLogEntry *entry = log->current_entry;
+
+ if (lv->customdata) {
+ BLI_mempool_free(entry->vdata.pool, lv->customdata);
+ lv->customdata = NULL;
+ }
+
+ CustomData_bmesh_copy_data(&bm->vdata, &entry->vdata, v->head.data, &lv->customdata);
+#endif
+}
+
+static void bm_log_face_customdata(BMesh *bm, BMLog *log, BMFace *f, BMLogFace *lf)
+{
+#ifdef CUSTOMDATA
+ // if (!lf) {
+ // return;
+ //}
+ BMLogEntry *entry = log->current_entry;
+ uint f_id = bm_log_face_id_get(log, f);
+ void *key = POINTER_FROM_UINT(f_id);
+
+ BLI_ghash_insert(log->current_entry->modified_faces, key, lf);
+
+ BMLoop *l1 = f->l_first;
+ BMLoop *l2 = f->l_first->next;
+ BMLoop *l3 = f->l_first->prev;
+ BMLoop *ls[3] = {l1, l2, l3};
+
+ for (int i = 0; i < 3; i++) {
+ if (lf->customdata[i]) {
+ BLI_mempool_free(entry->ldata.pool, lf->customdata[i]);
+ lf->customdata[i] = NULL;
+ }
+
+ CustomData_bmesh_copy_data(&bm->ldata, &entry->ldata, ls[i]->head.data, &lf->customdata[i]);
+ }
+#endif
+}
+
/* Get a vertex's paint-mask value
*
* Returns zero if no paint-mask layer is present */
@@ -212,6 +265,7 @@ static BMLogVert *bm_log_vert_alloc(BMLog *log, BMVert *v, const int cd_vert_mas
{
BMLogEntry *entry = log->current_entry;
BMLogVert *lv = BLI_mempool_alloc(entry->pool_verts);
+ lv->customdata = NULL;
bm_log_vert_bmvert_copy(lv, v, cd_vert_mask_offset);
@@ -225,6 +279,7 @@ static BMLogFace *bm_log_face_alloc(BMLog *log, BMFace *f)
BMLogFace *lf = BLI_mempool_alloc(entry->pool_faces);
BMVert *v[3];
+ lf->customdata[0] = lf->customdata[1] = lf->customdata[2] = NULL;
BLI_assert(f->len == 3);
// BM_iter_as_array(NULL, BM_VERTS_OF_FACE, f, (void **)v, 3);
@@ -285,7 +340,7 @@ static void bm_log_faces_unmake(BMesh *bm, BMLog *log, GHash *faces)
}
}
-static void bm_log_verts_restore(BMesh *bm, BMLog *log, GHash *verts)
+static void bm_log_verts_restore(BMesh *bm, BMLog *log, GHash *verts, BMLogEntry *entry)
{
const int cd_vert_mask_offset = CustomData_get_offset(&bm->vdata, CD_PAINT_MASK);
@@ -298,6 +353,12 @@ static void bm_log_verts_restore(BMesh *bm, BMLog *log, GHash *verts)
v->head.hflag = lv->hflag;
normal_short_to_float_v3(v->no, lv->no);
bm_log_vert_id_set(log, v, POINTER_AS_UINT(key));
+
+#ifdef CUSTOMDATA
+ if (lv->customdata) {
+ CustomData_bmesh_copy_data(&bm->vdata, &entry->vdata, lv->customdata, &v->head.data);
+ }
+#endif
}
}
@@ -641,6 +702,31 @@ void BM_log_mesh_elems_reorder(BMesh *bm, BMLog *log)
MEM_freeN(farr);
}
+BMLogEntry *BM_log_entry_check_customdata(BMesh *bm, BMLog *log)
+{
+ BMLogEntry *entry = log->current_entry;
+
+ if (!entry) {
+ return BM_log_entry_add_ex(bm, log, false);
+ }
+
+#ifndef CUSTOMDATA
+ return entry;
+#else
+
+ CustomData *cd1[4] = {&bm->vdata, &bm->edata, &bm->ldata, &bm->pdata};
+ CustomData *cd2[4] = {&entry->vdata, &entry->edata, &entry->ldata, &entry->pdata};
+
+ for (int i = 0; i < 4; i++) {
+ if (!CustomData_layout_is_same(cd1[i], cd2[i])) {
+ return BM_log_entry_add_ex(bm, log, true);
+ }
+ }
+
+ return entry;
+#endif
+}
+
/* Start a new log entry and update the log entry list
*
* If the log entry list is empty, or if the current log entry is the
@@ -651,8 +737,15 @@ void BM_log_mesh_elems_reorder(BMesh *bm, BMLog *log)
*
* In either case, the new entry is set as the current log entry.
*/
-BMLogEntry *BM_log_entry_add(BMLog *log)
+BMLogEntry *BM_log_entry_add(BMesh *bm, BMLog *log)
{
+ return BM_log_entry_add_ex(bm, log, false);
+}
+
+BMLogE
@@ Diff output truncated at 10240 characters. @@
More information about the Bf-blender-cvs
mailing list