[Bf-blender-cvs] [3e5431fdf43] master: Sculpt: Invert Smooth to Enhance Details

Pablo Dobarro noreply at git.blender.org
Tue Aug 18 16:15:07 CEST 2020


Commit: 3e5431fdf43906cd900f960f65ef8897e8a108a3
Author: Pablo Dobarro
Date:   Tue Aug 18 16:13:43 2020 +0200
Branches: master
https://developer.blender.org/rB3e5431fdf43906cd900f960f65ef8897e8a108a3

Sculpt: Invert Smooth to Enhance Details

This enables the invert mode in the smooth brush as Enhance Details.
The operation is similar to the Sharpen Filter intensify details parameter,
which consist in applying the laplacian smooth displacement in the opposite
direction calculated using the original coordinates.

Reviewed By: sergey

Differential Revision: https://developer.blender.org/D8509

===================================================================

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/makesrna/intern/rna_brush.c

===================================================================

diff --git a/source/blender/editors/sculpt_paint/sculpt.c b/source/blender/editors/sculpt_paint/sculpt.c
index 03d079ba0e1..5d09109c506 100644
--- a/source/blender/editors/sculpt_paint/sculpt.c
+++ b/source/blender/editors/sculpt_paint/sculpt.c
@@ -2331,7 +2331,7 @@ static float brush_strength(const Sculpt *sd,
       }
 
     case SCULPT_TOOL_SMOOTH:
-      return alpha * pressure * feather;
+      return flip * alpha * pressure * feather;
 
     case SCULPT_TOOL_PINCH:
       if (flip > 0.0f) {
@@ -6365,6 +6365,7 @@ void SCULPT_cache_free(StrokeCache *cache)
   MEM_SAFE_FREE(cache->surface_smooth_laplacian_disp);
   MEM_SAFE_FREE(cache->layer_displacement_factor);
   MEM_SAFE_FREE(cache->prev_colors);
+  MEM_SAFE_FREE(cache->detail_directions);
 
   if (cache->pose_ik_chain) {
     SCULPT_pose_ik_chain_free(cache->pose_ik_chain);
diff --git a/source/blender/editors/sculpt_paint/sculpt_intern.h b/source/blender/editors/sculpt_paint/sculpt_intern.h
index 65006031bb3..caa36a909fe 100644
--- a/source/blender/editors/sculpt_paint/sculpt_intern.h
+++ b/source/blender/editors/sculpt_paint/sculpt_intern.h
@@ -889,6 +889,9 @@ typedef struct StrokeCache {
   /* Pose brush */
   struct SculptPoseIKChain *pose_ik_chain;
 
+  /* Enhance Details. */
+  float (*detail_directions)[3];
+
   /* Clay Thumb brush */
   /* Angle of the front tilting plane of the brush to simulate clay accumulation. */
   float clay_thumb_front_angle;
diff --git a/source/blender/editors/sculpt_paint/sculpt_smooth.c b/source/blender/editors/sculpt_paint/sculpt_smooth.c
index 2b93298ac4a..63fe8643628 100644
--- a/source/blender/editors/sculpt_paint/sculpt_smooth.c
+++ b/source/blender/editors/sculpt_paint/sculpt_smooth.c
@@ -195,6 +195,85 @@ void SCULPT_neighbor_color_average(SculptSession *ss, float result[4], int index
   }
 }
 
+static void do_enhance_details_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;
+
+  PBVHVertexIter vd;
+
+  float bstrength = ss->cache->bstrength;
+  CLAMP(bstrength, -1.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);
+  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,
+                                                                  vd.mask ? *vd.mask : 0.0f,
+                                                                  vd.index,
+                                                                  thread_id);
+
+      float disp[3];
+      madd_v3_v3v3fl(disp, vd.co, ss->cache->detail_directions[vd.index], fade);
+      SCULPT_clip(sd, ss, vd.co, disp);
+
+      if (vd.mvert) {
+        vd.mvert->flag |= ME_VERT_PBVH_UPDATE;
+      }
+    }
+  }
+  BKE_pbvh_vertex_iter_end;
+}
+
+static void SCULPT_enhance_details_brush(Sculpt *sd,
+                                         Object *ob,
+                                         PBVHNode **nodes,
+                                         const int totnode)
+{
+  SculptSession *ss = ob->sculpt;
+  Brush *brush = BKE_paint_brush(&sd->paint);
+
+  SCULPT_vertex_random_access_ensure(ss);
+  SCULPT_boundary_info_ensure(ob);
+
+  if (SCULPT_stroke_is_first_brush_step(ss->cache)) {
+    const int totvert = SCULPT_vertex_count_get(ss);
+    ss->cache->detail_directions = MEM_malloc_arrayN(
+        totvert, 3 * sizeof(float), "details directions");
+
+    for (int i = 0; i < totvert; i++) {
+      float avg[3];
+      SCULPT_neighbor_coords_average(ss, avg, i);
+      sub_v3_v3v3(ss->cache->detail_directions[i], avg, SCULPT_vertex_co_get(ss, i));
+    }
+  }
+
+  SculptThreadedTaskData data = {
+      .sd = sd,
+      .ob = ob,
+      .brush = brush,
+      .nodes = nodes,
+  };
+
+  TaskParallelSettings settings;
+  BKE_pbvh_parallel_range_settings(&settings, true, totnode);
+  BLI_task_parallel_range(0, totnode, &data, do_enhance_details_brush_task_cb_ex, &settings);
+}
+
 static void do_smooth_brush_task_cb_ex(void *__restrict userdata,
                                        const int n,
                                        const TaskParallelTLS *__restrict tls)
@@ -300,7 +379,14 @@ void SCULPT_smooth(Sculpt *sd,
 void SCULPT_do_smooth_brush(Sculpt *sd, Object *ob, PBVHNode **nodes, int totnode)
 {
   SculptSession *ss = ob->sculpt;
-  SCULPT_smooth(sd, ob, nodes, totnode, ss->cache->bstrength, false);
+  if (ss->cache->bstrength <= 0.0f) {
+    /* Invert mode, intensify details. */
+    SCULPT_enhance_details_brush(sd, ob, nodes, totnode);
+  }
+  else {
+    /* Regular mode, smooth. */
+    SCULPT_smooth(sd, ob, nodes, totnode, ss->cache->bstrength, false);
+  }
 }
 
 /* HC Smooth Algorithm. */
diff --git a/source/blender/makesrna/intern/rna_brush.c b/source/blender/makesrna/intern/rna_brush.c
index a3fa4fed575..cc39a5dbe8d 100644
--- a/source/blender/makesrna/intern/rna_brush.c
+++ b/source/blender/makesrna/intern/rna_brush.c
@@ -45,6 +45,16 @@ static const EnumPropertyItem prop_direction_items[] = {
     {0, NULL, 0, NULL, NULL},
 };
 
+static const EnumPropertyItem prop_smooth_direction_items[] = {
+    {0, "SMOOTH", ICON_ADD, "Smooth", "Smooth the surfae"},
+    {BRUSH_DIR_IN,
+     "ENHANCE_DETAILS",
+     ICON_REMOVE,
+     "Enhance Details",
+     "Enhance the surface detail"},
+    {0, NULL, 0, NULL, NULL},
+};
+
 static const EnumPropertyItem sculpt_stroke_method_items[] = {
     {0, "DOTS", 0, "Dots", "Apply paint on each mouse move step"},
     {BRUSH_DRAG_DOT, "DRAG_DOT", 0, "Drag Dot", "Allows a single dot to be carefully positioned"},
@@ -527,6 +537,7 @@ static bool rna_BrushCapabilitiesSculpt_has_direction_get(PointerRNA *ptr)
                SCULPT_TOOL_DRAW_SHARP,
                SCULPT_TOOL_CLAY,
                SCULPT_TOOL_CLAY_STRIPS,
+               SCULPT_TOOL_SMOOTH,
                SCULPT_TOOL_LAYER,
                SCULPT_TOOL_INFLATE,
                SCULPT_TOOL_BLOB,
@@ -795,7 +806,8 @@ static const EnumPropertyItem *rna_Brush_direction_itemf(bContext *C,
         case SCULPT_TOOL_CLAY:
         case SCULPT_TOOL_CLAY_STRIPS:
           return prop_direction_items;
-
+        case SCULPT_TOOL_SMOOTH:
+          return prop_smooth_direction_items;
         case SCULPT_TOOL_MASK:
           switch ((BrushMaskTool)me->mask_tool) {
             case BRUSH_MASK_DRAW:



More information about the Bf-blender-cvs mailing list