[Bf-blender-cvs] [901654dcbf3] temp_bmesh_multires: * Added a "color boundary" tool that tries to smooth out vcol boundaries
Joseph Eagar
noreply at git.blender.org
Wed Nov 4 04:08:59 CET 2020
Commit: 901654dcbf3498d2f0bb317d58556f9e0ede7602
Author: Joseph Eagar
Date: Tue Nov 3 19:08:37 2020 -0800
Branches: temp_bmesh_multires
https://developer.blender.org/rB901654dcbf3498d2f0bb317d58556f9e0ede7602
* Added a "color boundary" tool that tries to smooth out vcol boundaries
===================================================================
M source/blender/blenkernel/intern/brush.c
M source/blender/blenloader/intern/versioning_defaults.c
M source/blender/editors/sculpt_paint/sculpt.c
M source/blender/editors/sculpt_paint/sculpt_intern.h
M source/blender/editors/sculpt_paint/sculpt_smooth.c
M source/blender/makesdna/DNA_brush_types.h
M source/blender/makesrna/intern/rna_brush.c
===================================================================
diff --git a/source/blender/blenkernel/intern/brush.c b/source/blender/blenkernel/intern/brush.c
index 17243b328e8..330d4619605 100644
--- a/source/blender/blenkernel/intern/brush.c
+++ b/source/blender/blenkernel/intern/brush.c
@@ -1799,6 +1799,14 @@ void BKE_brush_sculpt_reset(Brush *br)
br->flag &= ~BRUSH_SPACE_ATTEN;
br->curve_preset = BRUSH_CURVE_SPHERE;
break;
+ case SCULPT_TOOL_VCOL_BOUNDARY:
+ br->flag &= ~BRUSH_SPACE_ATTEN;
+ br->spacing = 5;
+ br->alpha = 0.7f;
+ br->surface_smooth_shape_preservation = 0.5f;
+ br->surface_smooth_current_vertex = 0.5f;
+ br->surface_smooth_iterations = 4;
+ break;
default:
break;
}
@@ -1858,6 +1866,7 @@ void BKE_brush_sculpt_reset(Brush *br)
br->sub_col[2] = 0.005f;
break;
+ case SCULPT_TOOL_VCOL_BOUNDARY:
case SCULPT_TOOL_SIMPLIFY:
case SCULPT_TOOL_PAINT:
case SCULPT_TOOL_MASK:
diff --git a/source/blender/blenloader/intern/versioning_defaults.c b/source/blender/blenloader/intern/versioning_defaults.c
index 48a24755250..3af3c42fa5d 100644
--- a/source/blender/blenloader/intern/versioning_defaults.c
+++ b/source/blender/blenloader/intern/versioning_defaults.c
@@ -697,6 +697,14 @@ void BLO_update_defaults_startup_blend(Main *bmain, const char *app_template)
brush->sculpt_tool = SCULPT_TOOL_PAINT;
}
+ brush_name = "Color Boundary";
+ brush = BLI_findstring(&bmain->brushes, brush_name, offsetof(ID, name) + 2);
+ if (!brush) {
+ brush = BKE_brush_add(bmain, brush_name, OB_MODE_SCULPT);
+ id_us_min(&brush->id);
+ brush->sculpt_tool = SCULPT_TOOL_VCOL_BOUNDARY;
+ }
+
brush_name = "Smear";
brush = BLI_findstring(&bmain->brushes, brush_name, offsetof(ID, name) + 2);
if (!brush) {
diff --git a/source/blender/editors/sculpt_paint/sculpt.c b/source/blender/editors/sculpt_paint/sculpt.c
index 028c534b8fc..e7e6ae8c9ca 100644
--- a/source/blender/editors/sculpt_paint/sculpt.c
+++ b/source/blender/editors/sculpt_paint/sculpt.c
@@ -1512,6 +1512,7 @@ static bool sculpt_tool_needs_original(const char sculpt_tool)
SCULPT_TOOL_DRAW_SHARP,
SCULPT_TOOL_ELASTIC_DEFORM,
SCULPT_TOOL_SMOOTH,
+ SCULPT_TOOL_VCOL_BOUNDARY,
SCULPT_TOOL_BOUNDARY,
SCULPT_TOOL_POSE);
}
@@ -2733,6 +2734,8 @@ static float brush_strength(const Sculpt *sd,
case SCULPT_TOOL_SMOOTH:
return flip * alpha * pressure * feather;
+ case SCULPT_TOOL_VCOL_BOUNDARY:
+ return flip * alpha * pressure * feather;
case SCULPT_TOOL_PINCH:
if (flip > 0.0f) {
@@ -6308,6 +6311,9 @@ static void do_brush_action(Sculpt *sd, Object *ob, Brush *brush, UnifiedPaintSe
case SCULPT_TOOL_PAINT:
SCULPT_do_paint_brush(sd, ob, nodes, totnode);
break;
+ case SCULPT_TOOL_VCOL_BOUNDARY:
+ SCULPT_smooth_vcol_boundary(sd, ob, nodes, totnode);
+ break;
case SCULPT_TOOL_SMEAR:
SCULPT_do_smear_brush(sd, ob, nodes, totnode);
break;
diff --git a/source/blender/editors/sculpt_paint/sculpt_intern.h b/source/blender/editors/sculpt_paint/sculpt_intern.h
index c751e26633b..0779eae4588 100644
--- a/source/blender/editors/sculpt_paint/sculpt_intern.h
+++ b/source/blender/editors/sculpt_paint/sculpt_intern.h
@@ -519,6 +519,11 @@ void SCULPT_neighbor_coords_average_interior(SculptSession *ss,
float result[3],
SculptVertRef index);
+void SCULPT_smooth_vcol_boundary(Sculpt *sd,
+ Object *ob,
+ PBVHNode **nodes,
+ const int totnode);
+
void SCULPT_smooth(Sculpt *sd,
Object *ob,
PBVHNode **nodes,
diff --git a/source/blender/editors/sculpt_paint/sculpt_smooth.c b/source/blender/editors/sculpt_paint/sculpt_smooth.c
index 18ba44844ca..c92611e7481 100644
--- a/source/blender/editors/sculpt_paint/sculpt_smooth.c
+++ b/source/blender/editors/sculpt_paint/sculpt_smooth.c
@@ -299,8 +299,7 @@ static void SCULPT_enhance_details_brush(Sculpt *sd,
}
#ifdef PROXY_ADVANCED
-static void do_smooth_brush_task_cb_ex(
- void *__restrict userdata,
+static void do_smooth_brush_task_cb_ex(void *__restrict userdata,
const int n,
const TaskParallelTLS *__restrict tls)
{
@@ -348,7 +347,7 @@ static void do_smooth_brush_task_cb_ex(
while (ni < MAX_PROXY_NEIGHBORS && p->neighbors[i][ni].node >= 0) {
ProxyKey *key = p->neighbors[i] + ni;
PBVHNode *n2 = ss->pbvh->nodes + key->node;
-
+
// printf("%d %d %d %p\n", key->node, key->pindex, ss->pbvh->totnode, n2);
if (key->pindex < 0 || key->pindex >= n2->proxyverts.size) {
@@ -675,3 +674,179 @@ void SCULPT_do_surface_smooth_brush(Sculpt *sd, Object *ob, PBVHNode **nodes, in
0, totnode, &data, SCULPT_do_surface_smooth_brush_displace_task_cb_ex, &settings);
}
}
+
+static void do_smooth_vcol_boundary_brush_task_cb_ex(void *__restrict userdata,
+ const int n,
+ const TaskParallelTLS *__restrict tls)
+{
+ SculptThreadedTaskData *data = userdata;
+ SculptSession *ss = data->ob->sculpt;
+ Sculpt *sd = data->sd;
+ const Brush *brush = data->brush;
+ const bool smooth_mask = data->smooth_mask;
+ float bstrength = data->strength;
+
+ PBVHVertexIter vd;
+
+ CLAMP(bstrength, 0.0f, 1.0f);
+
+ SculptBrushTest test;
+ SculptBrushTestFn sculpt_brush_test_sq_fn = SCULPT_brush_test_init_with_falloff_shape(
+ ss, &test, data->brush->falloff_shape);
+
+ const int thread_id = BLI_task_parallel_thread_id(tls);
+
+ float avg[4] = {0.0f, 0.0f, 0.0f, 0.0f};
+ float tot = 0.0f;
+ BKE_pbvh_vertex_iter_begin(ss->pbvh, data->nodes[n], vd, PBVH_ITER_UNIQUE)
+ {
+ if (!vd.col) {
+ continue;
+ }
+
+ if (sculpt_brush_test_sq_fn(&test, vd.co)) {
+ const float fade = bstrength * SCULPT_brush_strength_factor(
+ ss,
+ brush,
+ vd.co,
+ sqrtf(test.dist),
+ vd.no,
+ vd.fno,
+ smooth_mask ? 0.0f : (vd.mask ? *vd.mask : 0.0f),
+ vd.vertex,
+ thread_id);
+
+ madd_v3_v3fl(avg, vd.col, fade);
+ tot += fade;
+ }
+ }
+ BKE_pbvh_vertex_iter_end;
+
+ if (tot == 0.0f) {
+ return;
+ }
+ tot = 1.0f / tot;
+
+ mul_v3_fl(avg, tot);
+
+ BKE_pbvh_vertex_iter_begin(ss->pbvh, data->nodes[n], vd, PBVH_ITER_UNIQUE)
+ {
+ if (sculpt_brush_test_sq_fn(&test, vd.co)) {
+ const float fade = bstrength * SCULPT_brush_strength_factor(
+ ss,
+ brush,
+ vd.co,
+ sqrtf(test.dist),
+ vd.no,
+ vd.fno,
+ smooth_mask ? 0.0f : (vd.mask ? *vd.mask : 0.0f),
+ vd.vertex,
+ thread_id);
+ if (!vd.col) {
+ continue;
+ }
+
+ float avg2[3], val[3];
+ float tot2 = 0.0f;
+
+ zero_v3(avg2);
+
+ copy_v4_v4(avg, vd.col);
+
+ madd_v3_v3fl(avg2, vd.co, 0.5f);
+ tot2 += 0.5f;
+
+ SculptVertexNeighborIter ni;
+ SCULPT_VERTEX_NEIGHBORS_ITER_BEGIN (ss, vd.vertex, ni) {
+ const float *col = SCULPT_vertex_color_get(ss, ni.vertex);
+ const float *co = SCULPT_vertex_co_get(ss, ni.vertex);
+
+ //simple color metric
+ float dv[4];
+ sub_v4_v4v4(dv, col, avg);
+ float w = (fabs(dv[0]) + fabs(dv[1]) + fabs(dv[2]) + fabs(dv[3])) / 4.0;
+
+ //w = 1.0f - w;
+ //w = fabs(0.5 - w);
+ w *= w * w;
+
+ madd_v3_v3fl(avg2, co, w);
+ tot2 += w;
+ }
+ SCULPT_VERTEX_NEIGHBORS_ITER_END(ni);
+
+ if (tot2 == 0.0) {
+ continue;
+ }
+
+ mul_v3_fl(avg2, 1.0 / tot2);
+
+ sub_v3_v3v3(val, avg2, vd.co);
+ madd_v3_v3v3fl(val, vd.co, val, fade);
+ SCULPT_clip(sd, ss, vd.co, val);
+
+ if (vd.mvert) {
+ vd.mvert->flag |= ME_VERT_PBVH_UPDATE;
+ }
+ }
+ }
+ BKE_pbvh_vertex_iter_end;
+}
+
+void SCULPT_smooth_vcol_boundary(Sculpt *sd, Object *ob, PBVHNode **nodes, const int totnode)
+{
+ SculptSession *ss = ob->sculpt;
+
+ Brush *brush = BKE_paint_brush(&sd->paint);
+ float bstrength = ss->cache->bstrength;
+
+ const int max_iterations = 4;
+ const float fract = 1.0f / max_iterations;
+ PBVHType type = BKE_pbvh_type(ss->pbvh);
+ int iteration, count;
+ float last;
+
+ CLAMP(bstrength, 0.0f, 1.0f);
+
+ count = (int)(bstrength * max_iterations);
+ last = max_iterations * (bstrength - count * fract);
+
+ if (type == PBVH_FACES && !ss->pmap) {
+ BLI_assert(!"sculpt smooth: pmap missing");
+ return;
+ }
+
+ if (type != PBVH_BMESH) {
+ SCULPT_vertex_random_access_ensure(ss);
+ }
+
+ SCULPT_boundary_info_ensure(ob);
+
+#ifdef PROXY_ADVANCED
+ int datamask = PV_CO | PV_NEIGHBORS | PV_NO | PV_INDEX | PV_MASK;
+ BKE_pbvh_ensure_proxyarrays(ss, ss->pbvh, nodes, totnode, datamask);
+
+ BKE_pbvh_load_proxyarrays(ss->pbvh, nodes, totnode, PV_CO | PV_NO | PV_MASK);
+#endif
+ for (iteration = 0; iteration <= count; iteration++) {
+ const float strength = (iteration != count) ? 1.0f : last;
+
+ SculptThreadedTaskData data = {
+ .sd = sd,
+ .ob = ob,
+ .brush = brush,
+ .nodes = nodes,
+ .smooth_mask = false,
+ .strength = strength,
+ };
+
+ TaskParallelSettings settings;
+ BKE_pbvh_parallel_range_settings(&settings, true, totnode);
+ BLI_task_paral
@@ Diff output truncated at 10240 characters. @@
More information about the Bf-blender-cvs
mailing list