[Bf-blender-cvs] [e36ae3c1e44] sculpt-mode-features: Merge branch 'master' into sculpt-mode-features

Pablo Dobarro noreply at git.blender.org
Fri May 31 23:12:04 CEST 2019


Commit: e36ae3c1e44a34f91f166839ead58bb5420b50e0
Author: Pablo Dobarro
Date:   Fri May 31 23:10:45 2019 +0200
Branches: sculpt-mode-features
https://developer.blender.org/rBe36ae3c1e44a34f91f166839ead58bb5420b50e0

Merge branch 'master' into sculpt-mode-features

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



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

diff --cc source/blender/editors/sculpt_paint/sculpt.c
index 975889c7498,4e5c2a74023..131424ff592
--- a/source/blender/editors/sculpt_paint/sculpt.c
+++ b/source/blender/editors/sculpt_paint/sculpt.c
@@@ -7054,33 -6021,7 +7054,33 @@@ static void sculpt_init_session(Depsgra
  
    ob->sculpt = MEM_callocN(sizeof(SculptSession), "sculpt session");
    ob->sculpt->mode_type = OB_MODE_SCULPT;
 +
 +  /* Create the customdalayer for vcol for testing */
 +  Mesh *me = ob->data;
 +  if (!CustomData_has_layer(&me->vdata, CD_MVERTCOL)) {
 +    ob->sculpt->vcol = CustomData_add_layer_named(
 +        &me->vdata, CD_MVERTCOL, CD_CALLOC, NULL, me->totvert, "vcols");
 +    for (int i = 0; i < me->totvert; i++) {
 +      ob->sculpt->vcol[i].r = 255;
 +      ob->sculpt->vcol[i].g = 255;
 +      ob->sculpt->vcol[i].b = 255;
 +      ob->sculpt->vcol[i].a = 255;
 +    }
 +  }
 +  else {
 +    ob->sculpt->vcol = CustomData_get_layer(&me->vdata, CD_MVERTCOL);
 +  }
 +
 +  /* init sculpt pivot */
 +  zero_v3(ob->sculpt->pivot_pos);
 +  zero_v4(ob->sculpt->pivot_rot);
 +  ob->sculpt->pivot_rot[3] = 1.0f;
 +
 +  zero_v3(ob->sculpt->init_pivot_pos);
 +  zero_v4(ob->sculpt->init_pivot_rot);
 +  ob->sculpt->init_pivot_rot[3] = 1.0f;
 +
-   BKE_sculpt_update_mesh_elements(depsgraph, scene, scene->toolsettings->sculpt, ob, false, false);
+   BKE_sculpt_update_object_for_edit(depsgraph, ob, false, false);
  }
  
  static int ed_object_sculptmode_flush_recalc_flag(Scene *scene,
@@@ -7599,1436 -6513,6 +7599,1436 @@@ static void SCULPT_OT_set_detail_size(w
    ot->flag = OPTYPE_REGISTER | OPTYPE_UNDO;
  }
  
 +#define MESH_FILTER_RANDOM_MOD 50
 +
 +static void filter_cache_init_task_cb(void *__restrict userdata,
 +                                      const int i,
 +                                      const ParallelRangeTLS *__restrict UNUSED(tls))
 +{
 +  SculptThreadedTaskData *data = userdata;
 +  SculptSession *ss = data->ob->sculpt;
 +  PBVHNode *node = data->nodes[i];
 +
 +  PBVHVertexIter vd;
 +  BKE_pbvh_vertex_iter_begin(ss->pbvh, node, vd, PBVH_ITER_UNIQUE)
 +  {
 +    int vi = vd.vert_indices[vd.i];
 +    if (vd.mask && (*vd.mask) < 1.0f) {
 +      data->node_mask[i] = 1;
 +    }
 +    copy_v3_v3(ss->filter_cache->orco[vi], ss->mvert[vi].co);
 +    if (data->filter_type && vi < MESH_FILTER_RANDOM_MOD) {
 +      data->random_disp[vi % MESH_FILTER_RANDOM_MOD] = (float)rand() / (float)(RAND_MAX);
 +    }
 +  }
 +  BKE_pbvh_vertex_iter_end;
 +
 +  if (data->node_mask[i] == 1) {
 +    if (data->init_colors) {
 +      sculpt_undo_push_node(data->ob, node, SCULPT_UNDO_COLOR);
 +    }
 +    else {
 +      sculpt_undo_push_node(data->ob, node, SCULPT_UNDO_COORDS);
 +    }
 +  }
 +}
 +
 +static void sculpt_filter_cache_init(Object *ob, Sculpt *sd, bool init_random, bool init_colors)
 +{
 +  SculptSession *ss = ob->sculpt;
 +  PBVH *pbvh = ob->sculpt->pbvh;
 +  PBVHNode **nodes;
 +  int totnode;
 +
 +  ss->filter_cache = MEM_callocN(sizeof(FilterCache), "filter cache");
 +  ss->filter_cache->orco = MEM_mallocN(3 * ss->totvert * sizeof(float), "orco");
 +  if (init_random) {
 +    ss->filter_cache->random_disp = MEM_mallocN(MESH_FILTER_RANDOM_MOD * sizeof(float),
 +                                                "random_disp");
 +  }
 +
 +  if (init_colors && ss->vcol) {
 +    ss->filter_cache->orvcol = MEM_dupallocN(ss->vcol);
 +  }
 +
 +  SculptSearchSphereData searchdata = {
 +      .ss = ss,
 +      .sd = sd,
 +      .radius_squared = FLT_MAX,
 +  };
 +  BKE_pbvh_search_gather(pbvh, sculpt_search_sphere_cb, &searchdata, &nodes, &totnode);
 +
 +  int *node_mask = MEM_callocN(totnode * sizeof(int), "node mask");
 +  for (int i = 0; i < totnode; i++) {
 +    node_mask[i] = 0;
 +  }
 +
 +  int filter_type;
 +  if (init_random) {
 +    filter_type = 1;
 +  }
 +  else {
 +    filter_type = 0;
 +  }
 +
 +  SculptThreadedTaskData data = {
 +      .sd = sd,
 +      .ob = ob,
 +      .nodes = nodes,
 +      .filter_type = filter_type,
 +      .init_colors = init_colors,
 +      .random_disp = ss->filter_cache->random_disp,
 +      .node_mask = node_mask,
 +  };
 +
 +  ParallelRangeSettings settings;
 +  BLI_parallel_range_settings_defaults(&settings);
 +  settings.use_threading = ((sd->flags & SCULPT_USE_OPENMP) && totnode > SCULPT_THREADED_LIMIT);
 +  BLI_task_parallel_range(0, totnode, &data, filter_cache_init_task_cb, &settings);
 +
 +  int tot_active_nodes = 0;
 +  int active_node_index = 0;
 +  PBVHNode **active_nodes;
 +
 +  for (int i = 0; i < totnode; i++) {
 +    if (node_mask[i] == 1) {
 +      tot_active_nodes++;
 +    }
 +  }
 +
 +  active_nodes = MEM_callocN(tot_active_nodes * sizeof(PBVHNode *), "active nodes");
 +
 +  for (int i = 0; i < totnode; i++) {
 +    if (node_mask[i] == 1) {
 +      active_nodes[active_node_index] = nodes[i];
 +      active_node_index++;
 +    }
 +  }
 +
 +  ss->filter_cache->nodes = active_nodes;
 +  ss->filter_cache->totnode = tot_active_nodes;
 +
 +  if (nodes) {
 +    MEM_freeN(nodes);
 +  }
 +
 +  if (node_mask) {
 +    MEM_freeN(node_mask);
 +  }
 +}
 +
 +static void sculpt_filter_cache_free(SculptSession *ss)
 +{
 +  MEM_freeN(ss->filter_cache->orco);
 +  MEM_freeN(ss->filter_cache->nodes);
 +  if (ss->filter_cache->random_disp) {
 +    MEM_freeN(ss->filter_cache->random_disp);
 +  }
 +  if (ss->filter_cache->orvcol) {
 +    MEM_freeN(ss->filter_cache->orvcol);
 +  }
 +  MEM_freeN(ss->filter_cache);
 +}
 +
 +typedef enum eSculptMeshFilterTypes {
 +  MESH_FILTER_SMOOTH = 0,
 +  MESH_FILTER_GROW = 1,
 +  MESH_FILTER_SCALE = 2,
 +  MESH_FILTER_DILATE = 3,
 +  MESH_FILTER_SPHERE = 4,
 +  MESH_FILTER_RANDOM = 5,
 +  MESH_FILTER_RELAX = 6,
 +} eSculptMeshFilterTypes;
 +
 +EnumPropertyItem prop_mesh_filter_types[] = {
 +    {MESH_FILTER_SMOOTH, "SMOOTH", 0, "Smooth", "Smooth mesh"},
 +    // {MESH_FILTER_RELAX, "RELAX", 0, "Relax", "Relax mesh"},
 +    {MESH_FILTER_GROW, "GROW", 0, "Grow", "Grow mesh"},
 +    {MESH_FILTER_SCALE, "SCALE", 0, "Scale", "Scale mesh"},
 +    {MESH_FILTER_DILATE, "DILATE", 0, "Dilate", "Dilate mesh"},
 +    {MESH_FILTER_SPHERE, "SPHERE", 0, "Sphere", "Morph into sphere"},
 +    {MESH_FILTER_RANDOM, "RANDOM", 0, "Random", "Randomize mesh"},
 +    {0, NULL, 0, NULL, NULL},
 +};
 +
 +static void mesh_filter_task_cb(void *__restrict userdata,
 +                                const int i,
 +                                const ParallelRangeTLS *__restrict UNUSED(tls))
 +{
 +  SculptThreadedTaskData *data = userdata;
 +  SculptSession *ss = data->ob->sculpt;
 +  PBVHNode *node = data->nodes[i];
 +
 +  const int mode = data->filter_type;
 +
 +  PBVHVertexIter vd;
 +  BKE_pbvh_vertex_iter_begin(ss->pbvh, node, vd, PBVH_ITER_UNIQUE)
 +  {
 +    float orig_co[3], val[3], avg[3], normal[3], disp[3], disp2[3], transform[3][3];
 +    float fade = vd.mask ? *vd.mask : 1.0f;
 +    fade = 1 - fade;
 +    fade *= data->filter_strength;
 +    copy_v3_v3(orig_co, ss->filter_cache->orco[vd.vert_indices[vd.i]]);
 +    switch (mode) {
 +      case MESH_FILTER_SMOOTH:
 +        CLAMP(fade, -1.0f, 1.0f);
 +        neighbor_average(ss, avg, vd.vert_indices[vd.i]);
 +        sub_v3_v3v3(val, avg, orig_co);
 +        madd_v3_v3v3fl(val, orig_co, val, fade);
 +        sub_v3_v3v3(disp, val, orig_co);
 +        add_v3_v3v3(ss->mvert[vd.vert_indices[vd.i]].co, orig_co, disp);
 +        break;
 +      case MESH_FILTER_RELAX:
 +        relax_vertex(disp, vd, ss, true);
 +        add_v3_v3v3(ss->mvert[vd.vert_indices[vd.i]].co, orig_co, disp);
 +        break;
 +      case MESH_FILTER_DILATE:
 +        normal_short_to_float_v3(normal, vd.no);
 +        mul_v3_v3fl(disp, normal, fade);
 +        add_v3_v3v3(ss->mvert[vd.vert_indices[vd.i]].co, orig_co, disp);
 +        break;
 +      case MESH_FILTER_GROW:
 +        sub_v3_v3v3(disp, orig_co, data->ob->loc);
 +        normalize_v3(disp);
 +        mul_v3_fl(disp, fade);
 +        add_v3_v3v3(ss->mvert[vd.vert_indices[vd.i]].co, orig_co, disp);
 +      case MESH_FILTER_SCALE:
 +        unit_m3(transform);
 +        scale_m3_fl(transform, 1 + fade);
 +        copy_v3_v3(val, orig_co);
 +        mul_m3_v3(transform, val);
 +        sub_v3_v3v3(disp, val, orig_co);
 +        add_v3_v3v3(ss->mvert[vd.vert_indices[vd.i]].co, orig_co, disp);
 +        break;
 +      case MESH_FILTER_SPHERE:
 +        sub_v3_v3v3(disp, orig_co, data->ob->loc);
 +        normalize_v3(disp);
 +        if (fade > 0) {
 +          mul_v3_v3fl(disp, disp, fade);
 +        }
 +        else {
 +          mul_v3_v3fl(disp, disp, -fade);
 +        }
 +
 +        unit_m3(transform);
 +        if (fade > 0) {
 +          scale_m3_fl(transform, 1 - fade);
 +        }
 +        else {
 +          scale_m3_fl(transform, 1 + fade);
 +        }
 +        copy_v3_v3(val, orig_co);
 +        mul_m3_v3(transform, val);
 +        sub_v3_v3v3(disp2, val, orig_co);
 +
 +        mid_v3_v3v3(disp, disp, disp2);
 +        add_v3_v3v3(ss->mvert[vd.vert_indices[vd.i]].co, orig_co, disp);
 +        break;
 +      case MESH_FILTER_RANDOM:
 +        normal_short_to_float_v3(normal, vd.no);
 +        mul_v3_fl(normal,
 +                  data->random_disp[vd.vert_indices[vd.i] % MESH_FILTER_RANDOM_MOD] - 0.5f);
 +        mul_v3_v3fl(disp, normal, fade);
 +        add_v3_v3v3(ss->mvert[vd.vert_indices[vd.i]].co, orig_co, disp);
 +        break;
 +    }
 +    if (vd.mvert)
 +      vd.mvert->flag |= ME_VERT_PBVH_UPDATE;
 +  }
 +  BKE_pbvh_vertex_iter_end;
 +
 +  BKE_pbvh_node_mark_redraw(node);
 +}
 +
 +int sculpt_mesh_filter_modal(bContext *C, wmOperator *op, const wmEvent *event)
 +{
 +  ARegion *ar = CTX_wm_region(C);
 +  Object *ob = CTX_data_active_object(C);
 +  SculptSession *ss = ob->sculpt;
 +  Sculpt *sd = CTX_data_tool_settings(C)->sculpt;
 +  int mode = RNA_enum_get(op->ptr, "type");
 +  float filter_strength = RNA_float_get(op->ptr, "strength");
 +
 +  float len = event->prevclickx - event->mval[0];
 +  filter_strength = filter_strength * -len * 0.001f;
 +
 +  SculptThreadedTaskData data = {
 +      .sd = sd,
 +      .ob = ob,
 +      .nodes = ss->filter_cache->nodes,
 +      .smooth_value = 0.5f,
 +      .filter_type = mode,
 +      .filter_strength = filter_strength,
 +      .random_disp = ss->filter_cache->random_disp,
 +  };
 +
 +  Para

@@ Diff output truncated at 10240 characters. @@



More information about the Bf-blender-cvs mailing list