diff options
Diffstat (limited to 'source')
-rw-r--r-- | source/blender/blenkernel/BKE_paint.h | 3 | ||||
-rw-r--r-- | source/blender/blenkernel/BKE_pbvh.h | 1 | ||||
-rw-r--r-- | source/blender/blenkernel/intern/pbvh.c | 18 | ||||
-rw-r--r-- | source/blender/editors/sculpt_paint/sculpt.c | 93 |
4 files changed, 98 insertions, 17 deletions
diff --git a/source/blender/blenkernel/BKE_paint.h b/source/blender/blenkernel/BKE_paint.h index 8c925ee2ae1..f4b485ae53a 100644 --- a/source/blender/blenkernel/BKE_paint.h +++ b/source/blender/blenkernel/BKE_paint.h @@ -334,6 +334,9 @@ typedef struct SculptSession { /* Cursor data and active vertex for tools */ int active_vertex_index; + int active_face_index; + int active_grid_index; + float cursor_radius; float cursor_location[3]; float cursor_normal[3]; diff --git a/source/blender/blenkernel/BKE_pbvh.h b/source/blender/blenkernel/BKE_pbvh.h index b4f16bfd899..2020d45ae86 100644 --- a/source/blender/blenkernel/BKE_pbvh.h +++ b/source/blender/blenkernel/BKE_pbvh.h @@ -155,6 +155,7 @@ bool BKE_pbvh_node_raycast(PBVH *bvh, struct IsectRayPrecalc *isect_precalc, float *depth, int *active_vertex_index, + int *active_face_grid_index, float *face_normal); bool BKE_pbvh_bmesh_node_raycast_detail(PBVHNode *node, diff --git a/source/blender/blenkernel/intern/pbvh.c b/source/blender/blenkernel/intern/pbvh.c index ac0c9d030cf..879f1e507ba 100644 --- a/source/blender/blenkernel/intern/pbvh.c +++ b/source/blender/blenkernel/intern/pbvh.c @@ -2121,6 +2121,7 @@ static bool pbvh_faces_node_raycast(PBVH *bvh, struct IsectRayPrecalc *isect_precalc, float *depth, int *r_active_vertex_index, + int *r_active_face_index, float *r_face_normal) { const MVert *vert = bvh->verts; @@ -2166,6 +2167,7 @@ static bool pbvh_faces_node_raycast(PBVH *bvh, if (len_squared_v3v3(location, co[j]) < len_squared_v3v3(location, nearest_vertex_co)) { copy_v3_v3(nearest_vertex_co, co[j]); *r_active_vertex_index = mloop[lt->tri[j]].v; + *r_active_face_index = lt->poly; } } } @@ -2183,6 +2185,7 @@ static bool pbvh_grids_node_raycast(PBVH *bvh, struct IsectRayPrecalc *isect_precalc, float *depth, int *r_active_vertex_index, + int *r_active_grid_index, float *r_face_normal) { const int totgrid = node->totprim; @@ -2236,15 +2239,23 @@ static bool pbvh_grids_node_raycast(PBVH *bvh, if (r_active_vertex_index) { float location[3] = {0.0}; madd_v3_v3v3fl(location, ray_start, ray_normal, *depth); + + const int x_it[4] = {0, 1, 1, 0}; + const int y_it[4] = {0, 0, 1, 1}; + for (int j = 0; j < 4; j++) { if (len_squared_v3v3(location, co[j]) < len_squared_v3v3(location, nearest_vertex_co)) { copy_v3_v3(nearest_vertex_co, co[j]); - *r_active_vertex_index = gridkey->grid_area * grid_index + y * gridkey->grid_size + - x; + + *r_active_vertex_index = gridkey->grid_area * grid_index + + (y + y_it[j]) * gridkey->grid_size + (x + x_it[j]); } } } + if (r_active_grid_index) { + *r_active_grid_index = grid_index; + } } } } @@ -2266,6 +2277,7 @@ bool BKE_pbvh_node_raycast(PBVH *bvh, struct IsectRayPrecalc *isect_precalc, float *depth, int *active_vertex_index, + int *active_face_grid_index, float *face_normal) { bool hit = false; @@ -2284,6 +2296,7 @@ bool BKE_pbvh_node_raycast(PBVH *bvh, isect_precalc, depth, active_vertex_index, + active_face_grid_index, face_normal); break; case PBVH_GRIDS: @@ -2295,6 +2308,7 @@ bool BKE_pbvh_node_raycast(PBVH *bvh, isect_precalc, depth, active_vertex_index, + active_face_grid_index, face_normal); break; case PBVH_BMESH: diff --git a/source/blender/editors/sculpt_paint/sculpt.c b/source/blender/editors/sculpt_paint/sculpt.c index dbb89617b08..91c8262dd67 100644 --- a/source/blender/editors/sculpt_paint/sculpt.c +++ b/source/blender/editors/sculpt_paint/sculpt.c @@ -216,6 +216,22 @@ static void SCULPT_active_vertex_normal_get(SculptSession *ss, float normal[3]) /* Sculpt Face Sets and Visibility. */ +static int SCULPT_active_face_set_get(SculptSession *ss) +{ + switch (BKE_pbvh_type(ss->pbvh)) { + case PBVH_FACES: + return ss->face_sets[ss->active_face_index]; + case PBVH_GRIDS: { + const int face_index = BKE_subdiv_cgg_grid_to_face_index(ss->subdiv_ccg, + ss->active_grid_index); + return ss->face_sets[face_index]; + } + case PBVH_BMESH: + return SCULPT_FACE_SET_NONE; + } + return SCULPT_FACE_SET_NONE; +} + static void SCULPT_vertex_visible_set(SculptSession *ss, int index, bool visible) { switch (BKE_pbvh_type(ss->pbvh)) { @@ -2997,6 +3013,8 @@ typedef struct { int active_vertex_index; float *face_normal; + int active_face_grid_index; + struct IsectRayPrecalc isect_precalc; } SculptRaycastData; @@ -3641,19 +3659,49 @@ static void do_draw_face_sets_brush_task_cb_ex(void *__restrict userdata, 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, - tls->thread_id); + if (BKE_pbvh_type(ss->pbvh) == PBVH_FACES) { + MeshElemMap *vert_map = &ss->pmap[vd.index]; + for (int j = 0; j < ss->pmap[vd.index].count; j++) { + const MPoly *p = &ss->mpoly[vert_map->indices[j]]; - if (fade > 0.05f) { - SCULPT_vertex_face_set_set(ss, vd.index, ss->cache->paint_face_set); + float poly_center[3]; + BKE_mesh_calc_poly_center(p, &ss->mloop[p->loopstart], ss->mvert, poly_center); + + if (sculpt_brush_test_sq_fn(&test, poly_center)) { + 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, + tls->thread_id); + + if (fade > 0.05f && ss->face_sets[vert_map->indices[j]] > 0) { + ss->face_sets[vert_map->indices[j]] = abs(ss->cache->paint_face_set); + } + } + } + } + + else if (BKE_pbvh_type(ss->pbvh) == PBVH_GRIDS) { + { + 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, + tls->thread_id); + + if (fade > 0.05f) { + SCULPT_vertex_face_set_set(ss, vd.index, ss->cache->paint_face_set); + } + } } } } @@ -3714,7 +3762,7 @@ static void do_draw_face_sets_brush(Sculpt *sd, Object *ob, PBVHNode **nodes, in ss->cache->radial_symmetry_pass == 0) { if (ss->cache->invert) { /* When inverting the brush, pick the paint face mask ID from the mesh. */ - ss->cache->paint_face_set = SCULPT_vertex_face_set_get(ss, SCULPT_active_vertex_get(ss)); + ss->cache->paint_face_set = SCULPT_active_face_set_get(ss); } else { /* By default create a new Face Sets. */ @@ -7440,6 +7488,7 @@ static void sculpt_raycast_cb(PBVHNode *node, void *data_v, float *tmin) &srd->isect_precalc, &srd->depth, &srd->active_vertex_index, + &srd->active_face_grid_index, srd->face_normal)) { srd->hit = true; *tmin = srd->depth; @@ -7590,6 +7639,21 @@ bool SCULPT_cursor_geometry_info_update(bContext *C, ss->active_vertex_index = srd.active_vertex_index; copy_v3_v3(out->active_vertex_co, SCULPT_active_vertex_co_get(ss)); + switch (BKE_pbvh_type(ss->pbvh)) { + case PBVH_FACES: + ss->active_face_index = srd.active_face_grid_index; + ss->active_grid_index = 0; + break; + case PBVH_GRIDS: + ss->active_face_index = 0; + ss->active_grid_index = srd.active_face_grid_index; + break; + case PBVH_BMESH: + ss->active_face_index = 0; + ss->active_grid_index = 0; + break; + } + copy_v3_v3(out->location, ray_normal); mul_v3_fl(out->location, srd.depth); add_v3_v3(out->location, ray_start); @@ -11710,8 +11774,7 @@ static int sculpt_face_sets_change_visibility_invoke(bContext *C, const int tot_vert = SCULPT_vertex_count_get(ss); const int mode = RNA_enum_get(op->ptr, "mode"); - int active_vertex_index = SCULPT_active_vertex_get(ss); - int active_face_set = SCULPT_vertex_face_set_get(ss, active_vertex_index); + const int active_face_set = SCULPT_active_face_set_get(ss); SCULPT_undo_push_begin("Hide area"); |