diff options
Diffstat (limited to 'source/blender/editors/mesh')
-rw-r--r-- | source/blender/editors/mesh/editface.c | 56 | ||||
-rw-r--r-- | source/blender/editors/mesh/editmesh_add.c | 2 | ||||
-rw-r--r-- | source/blender/editors/mesh/editmesh_bevel.c | 5 | ||||
-rw-r--r-- | source/blender/editors/mesh/editmesh_bisect.c | 20 | ||||
-rw-r--r-- | source/blender/editors/mesh/editmesh_extrude.c | 26 | ||||
-rw-r--r-- | source/blender/editors/mesh/editmesh_knife.c | 21 | ||||
-rw-r--r-- | source/blender/editors/mesh/editmesh_knife_project.c | 13 | ||||
-rw-r--r-- | source/blender/editors/mesh/editmesh_loopcut.c | 15 | ||||
-rw-r--r-- | source/blender/editors/mesh/editmesh_path.c | 16 | ||||
-rw-r--r-- | source/blender/editors/mesh/editmesh_select.c | 116 | ||||
-rw-r--r-- | source/blender/editors/mesh/editmesh_tools.c | 20 | ||||
-rw-r--r-- | source/blender/editors/mesh/editmesh_utils.c | 2 | ||||
-rw-r--r-- | source/blender/editors/mesh/mesh_data.c | 16 | ||||
-rw-r--r-- | source/blender/editors/mesh/mesh_navmesh.c | 5 | ||||
-rw-r--r-- | source/blender/editors/mesh/meshtools.c | 74 |
15 files changed, 260 insertions, 147 deletions
diff --git a/source/blender/editors/mesh/editface.c b/source/blender/editors/mesh/editface.c index 52ec22aaaf0..870eb68600a 100644 --- a/source/blender/editors/mesh/editface.c +++ b/source/blender/editors/mesh/editface.c @@ -107,7 +107,7 @@ void paintface_flush_flags(Object *ob, short flag) GPU_drawobject_free(dm); } - BKE_mesh_batch_cache_dirty(me, BKE_MESH_BATCH_DIRTY_PAINT); + BKE_mesh_batch_cache_dirty(me, BKE_MESH_BATCH_DIRTY_ALL); } void paintface_hide(Object *ob, const bool unselected) @@ -396,7 +396,7 @@ bool paintface_mouse_select(struct bContext *C, Object *ob, const int mval[2], b return true; } -int do_paintface_box_select(ViewContext *vc, rcti *rect, bool select, bool extend) +int do_paintface_box_select(const struct EvaluationContext *eval_ctx, ViewContext *vc, rcti *rect, bool select, bool extend) { Object *ob = vc->obact; Mesh *me; @@ -427,7 +427,7 @@ int do_paintface_box_select(ViewContext *vc, rcti *rect, bool select, bool exten } } - ED_view3d_backbuf_validate(vc); + ED_view3d_backbuf_validate(eval_ctx, vc); ibuf = IMB_allocImBuf(size[0], size[1], 32, IB_rect); rt = ibuf->rect; @@ -518,7 +518,7 @@ void paintvert_flush_flags(Object *ob) } } - BKE_mesh_batch_cache_dirty(me, BKE_MESH_BATCH_DIRTY_PAINT); + BKE_mesh_batch_cache_dirty(me, BKE_MESH_BATCH_DIRTY_ALL); } /* note: if the caller passes false to flush_flags, then they will need to run paintvert_flush_flags(ob) themselves */ void paintvert_deselect_all_visible(Object *ob, int action, bool flush_flags) @@ -801,25 +801,47 @@ void ED_mesh_mirrtopo_init(Mesh *me, DerivedMesh *dm, const int ob_mode, MirrTop qsort(topo_pairs, totvert, sizeof(MirrTopoVert_t), mirrtopo_vert_sort); - /* Since the loop starts at 2, we must define the last index where the hash's differ */ - last = ((totvert >= 2) && (topo_pairs[0].hash == topo_pairs[1].hash)) ? 0 : 1; + last = 0; /* Get the pairs out of the sorted hashes, note, totvert+1 means we can use the previous 2, * but you cant ever access the last 'a' index of MirrTopoPairs */ - for (a = 2; a <= totvert; a++) { - /* printf("I %d %ld %d\n", (a-last), MirrTopoPairs[a ].hash, MirrTopoPairs[a ].v_index ); */ - if ((a == totvert) || (topo_pairs[a - 1].hash != topo_pairs[a].hash)) { - if (a - last == 2) { - if (em) { - index_lookup[topo_pairs[a - 1].v_index] = (intptr_t)BM_vert_at_index(em->bm, topo_pairs[a - 2].v_index); - index_lookup[topo_pairs[a - 2].v_index] = (intptr_t)BM_vert_at_index(em->bm, topo_pairs[a - 1].v_index); + if (em) { + BMVert **vtable = em->bm->vtable; + for (a = 1; a <= totvert; a++) { + /* printf("I %d %ld %d\n", (a - last), MirrTopoPairs[a].hash, MirrTopoPairs[a].v_indexs); */ + if ((a == totvert) || (topo_pairs[a - 1].hash != topo_pairs[a].hash)) { + const int match_count = a - last; + if (match_count == 2) { + const int j = topo_pairs[a - 1].v_index, k = topo_pairs[a - 2].v_index; + index_lookup[j] = (intptr_t)vtable[k]; + index_lookup[k] = (intptr_t)vtable[j]; + } + else if (match_count == 1) { + /* Center vertex. */ + const int j = topo_pairs[a - 1].v_index; + index_lookup[j] = (intptr_t)vtable[j]; + } + last = a; + } + } + } + else { + /* same as above, for mesh */ + for (a = 1; a <= totvert; a++) { + if ((a == totvert) || (topo_pairs[a - 1].hash != topo_pairs[a].hash)) { + const int match_count = a - last; + if (match_count == 2) { + const int j = topo_pairs[a - 1].v_index, k = topo_pairs[a - 2].v_index; + index_lookup[j] = k; + index_lookup[k] = j; } - else { - index_lookup[topo_pairs[a - 1].v_index] = topo_pairs[a - 2].v_index; - index_lookup[topo_pairs[a - 2].v_index] = topo_pairs[a - 1].v_index; + else if (match_count == 1) { + /* Center vertex. */ + const int j = topo_pairs[a - 1].v_index; + index_lookup[j] = j; } + last = a; } - last = a; } } diff --git a/source/blender/editors/mesh/editmesh_add.c b/source/blender/editors/mesh/editmesh_add.c index 07fedffaf80..77772cfc8cc 100644 --- a/source/blender/editors/mesh/editmesh_add.c +++ b/source/blender/editors/mesh/editmesh_add.c @@ -233,7 +233,7 @@ static int add_primitive_circle_exec(bContext *C, wmOperator *op) if (!EDBM_op_call_and_selectf( em, op, "verts.out", false, - "create_circle segments=%i diameter=%f cap_ends=%b cap_tris=%b matrix=%m4 calc_uvs=%b", + "create_circle segments=%i radius=%f cap_ends=%b cap_tris=%b matrix=%m4 calc_uvs=%b", RNA_int_get(op->ptr, "vertices"), RNA_float_get(op->ptr, "radius"), cap_end, cap_tri, mat, calc_uvs)) { diff --git a/source/blender/editors/mesh/editmesh_bevel.c b/source/blender/editors/mesh/editmesh_bevel.c index a81add7a86e..6b4f3516338 100644 --- a/source/blender/editors/mesh/editmesh_bevel.c +++ b/source/blender/editors/mesh/editmesh_bevel.c @@ -150,6 +150,7 @@ static bool edbm_bevel_init(bContext *C, wmOperator *op, const bool is_modal) for (i = 0; i < NUM_VALUE_KINDS; i++) { opdata->shift_value[i] = -1.0f; + opdata->initial_length[i] = -1.0f; /* note: scale for OFFSET_VALUE will get overwritten in edbm_bevel_invoke */ opdata->scale[i] = value_scale_per_inch[i] / pixels_per_inch; @@ -300,7 +301,7 @@ static void edbm_bevel_calc_initial_length(wmOperator *op, const wmEvent *event, mlen[1] = opdata->mcenter[1] - event->mval[1]; len = len_v2(mlen); vmode = opdata->value_mode; - if (mode_changed) { + if (mode_changed || opdata->initial_length[vmode] == -1.0f) { /* If current value is not default start value, adjust len so that * the scaling and offset in edbm_bevel_mouse_set_value will * start at current value */ @@ -506,6 +507,8 @@ static int edbm_bevel_modal(bContext *C, wmOperator *op, const wmEvent *event) else if (opdata->value_mode == OFFSET_VALUE_PERCENT && type != BEVEL_AMT_PERCENT) opdata->value_mode = OFFSET_VALUE; RNA_property_enum_set(op->ptr, prop, type); + if (opdata->initial_length[opdata->value_mode] == -1.0f) + edbm_bevel_calc_initial_length(op, event, true); } /* Update offset accordingly to new offset_type. */ if (!has_numinput && diff --git a/source/blender/editors/mesh/editmesh_bisect.c b/source/blender/editors/mesh/editmesh_bisect.c index 9b6df11d470..c9f083e2089 100644 --- a/source/blender/editors/mesh/editmesh_bisect.c +++ b/source/blender/editors/mesh/editmesh_bisect.c @@ -50,6 +50,8 @@ #include "ED_screen.h" #include "ED_view3d.h" +#include "UI_resources.h" + #include "mesh_intern.h" /* own include */ #define USE_MANIPULATOR @@ -198,7 +200,7 @@ static int mesh_bisect_modal(bContext *C, wmOperator *op, const wmEvent *event) { View3D *v3d = CTX_wm_view3d(C); if (v3d && (v3d->twtype & V3D_MANIPULATOR_DRAW)) { - WM_manipulator_group_add("MESH_WGT_bisect"); + WM_manipulator_group_type_add("MESH_WGT_bisect"); } } #endif @@ -426,8 +428,8 @@ static void manipulator_mesh_bisect_update_from_op(ManipulatorGroup *man) RNA_property_float_get_array(op->ptr, man->data.prop_plane_no, plane_no); WM_manipulator_set_matrix_location(man->translate_z, plane_co); - WM_manipulator_set_matrix_location(man->translate_c, plane_co); WM_manipulator_set_matrix_location(man->rotate_c, plane_co); + /* translate_c location comes from the property. */ WM_manipulator_set_matrix_rotation_from_z_axis(man->translate_z, plane_no); @@ -594,7 +596,7 @@ static bool manipulator_mesh_bisect_poll(const bContext *C, wmManipulatorGroupTy { wmOperator *op = WM_operator_last_redo(C); if (op == NULL || !STREQ(op->type->idname, "MESH_OT_bisect")) { - WM_manipulator_group_remove_ptr_delayed(wgt); + WM_manipulator_group_type_remove_ptr_delayed(wgt); return false; } return true; @@ -615,12 +617,16 @@ static void manipulator_mesh_bisect_setup(const bContext *C, wmManipulatorGroup const wmManipulatorType *wt_grab = WM_manipulatortype_find("MANIPULATOR_WT_grab_3d", true); const wmManipulatorType *wt_dial = WM_manipulatortype_find("MANIPULATOR_WT_dial_3d", true); - man->translate_z = WM_manipulator_new_ptr(wt_arrow, mgroup, "translate_z", NULL); - man->translate_c = WM_manipulator_new_ptr(wt_grab, mgroup, "translate_c", NULL); - man->rotate_c = WM_manipulator_new_ptr(wt_dial, mgroup, "rotate_c", NULL); + man->translate_z = WM_manipulator_new_ptr(wt_arrow, mgroup, NULL); + man->translate_c = WM_manipulator_new_ptr(wt_grab, mgroup, NULL); + man->rotate_c = WM_manipulator_new_ptr(wt_dial, mgroup, NULL); + + UI_GetThemeColor3fv(TH_MANIPULATOR_PRIMARY, man->translate_z->color); + UI_GetThemeColor3fv(TH_MANIPULATOR_PRIMARY, man->translate_c->color); + UI_GetThemeColor3fv(TH_MANIPULATOR_SECONDARY, man->rotate_c->color); RNA_enum_set(man->translate_z->ptr, "draw_style", ED_MANIPULATOR_ARROW_STYLE_NORMAL); - RNA_enum_set(man->translate_c->ptr, "draw_style", ED_MANIPULATOR_GRAB_STYLE_RING); + RNA_enum_set(man->translate_c->ptr, "draw_style", ED_MANIPULATOR_GRAB_STYLE_RING_2D); WM_manipulator_set_flag(man->translate_c, WM_MANIPULATOR_DRAW_VALUE, true); WM_manipulator_set_flag(man->rotate_c, WM_MANIPULATOR_DRAW_VALUE, true); diff --git a/source/blender/editors/mesh/editmesh_extrude.c b/source/blender/editors/mesh/editmesh_extrude.c index d5b2a3d3b82..9bc01687122 100644 --- a/source/blender/editors/mesh/editmesh_extrude.c +++ b/source/blender/editors/mesh/editmesh_extrude.c @@ -53,6 +53,8 @@ #include "ED_transform.h" #include "ED_view3d.h" +#include "UI_resources.h" + #include "MEM_guardedalloc.h" #include "mesh_intern.h" /* own include */ @@ -759,7 +761,7 @@ static int edbm_spin_invoke(bContext *C, wmOperator *op, const wmEvent *UNUSED(e if (ret & OPERATOR_FINISHED) { /* Setup manipulators */ if (v3d && (v3d->twtype & V3D_MANIPULATOR_DRAW)) { - WM_manipulator_group_add("MESH_WGT_spin"); + WM_manipulator_group_type_add("MESH_WGT_spin"); } } #endif @@ -859,9 +861,9 @@ static void manipulator_mesh_spin_update_from_op(ManipulatorSpinGroup *man) RNA_property_float_get_array(op->ptr, man->data.prop_axis_no, plane_no); WM_manipulator_set_matrix_location(man->translate_z, plane_co); - WM_manipulator_set_matrix_location(man->translate_c, plane_co); WM_manipulator_set_matrix_location(man->rotate_c, plane_co); WM_manipulator_set_matrix_location(man->angle_z, plane_co); + /* translate_c location comes from the property. */ WM_manipulator_set_matrix_rotation_from_z_axis(man->translate_z, plane_no); WM_manipulator_set_matrix_rotation_from_z_axis(man->angle_z, plane_no); @@ -878,7 +880,7 @@ static void manipulator_mesh_spin_update_from_op(ManipulatorSpinGroup *man) normalize_v3(man->data.rotate_up); WM_manipulator_set_matrix_rotation_from_z_axis(man->translate_c, plane_no); - WM_manipulator_set_matrix_rotation_from_yz_axis(man->rotate_c, man->data.rotate_axis, plane_no); + WM_manipulator_set_matrix_rotation_from_yz_axis(man->rotate_c, plane_no, man->data.rotate_axis); /* show the axis instead of mouse cursor */ RNA_enum_set(man->rotate_c->ptr, "draw_options", @@ -1057,7 +1059,7 @@ static bool manipulator_mesh_spin_poll(const bContext *C, wmManipulatorGroupType { wmOperator *op = WM_operator_last_redo(C); if (op == NULL || !STREQ(op->type->idname, "MESH_OT_spin")) { - WM_manipulator_group_remove_ptr_delayed(wgt); + WM_manipulator_group_type_remove_ptr_delayed(wgt); return false; } return true; @@ -1078,13 +1080,19 @@ static void manipulator_mesh_spin_setup(const bContext *C, wmManipulatorGroup *m const wmManipulatorType *wt_grab = WM_manipulatortype_find("MANIPULATOR_WT_grab_3d", true); const wmManipulatorType *wt_dial = WM_manipulatortype_find("MANIPULATOR_WT_dial_3d", true); - man->translate_z = WM_manipulator_new_ptr(wt_arrow, mgroup, "translate_z", NULL); - man->translate_c = WM_manipulator_new_ptr(wt_grab, mgroup, "translate_c", NULL); - man->rotate_c = WM_manipulator_new_ptr(wt_dial, mgroup, "rotate_c", NULL); - man->angle_z = WM_manipulator_new_ptr(wt_dial, mgroup, "angle_z", NULL); + man->translate_z = WM_manipulator_new_ptr(wt_arrow, mgroup, NULL); + man->translate_c = WM_manipulator_new_ptr(wt_grab, mgroup, NULL); + man->rotate_c = WM_manipulator_new_ptr(wt_dial, mgroup, NULL); + man->angle_z = WM_manipulator_new_ptr(wt_dial, mgroup, NULL); + + UI_GetThemeColor3fv(TH_MANIPULATOR_PRIMARY, man->translate_z->color); + UI_GetThemeColor3fv(TH_MANIPULATOR_PRIMARY, man->translate_c->color); + UI_GetThemeColor3fv(TH_MANIPULATOR_SECONDARY, man->rotate_c->color); + UI_GetThemeColor3fv(TH_AXIS_Z, man->angle_z->color); + RNA_enum_set(man->translate_z->ptr, "draw_style", ED_MANIPULATOR_ARROW_STYLE_NORMAL); - RNA_enum_set(man->translate_c->ptr, "draw_style", ED_MANIPULATOR_GRAB_STYLE_RING); + RNA_enum_set(man->translate_c->ptr, "draw_style", ED_MANIPULATOR_GRAB_STYLE_RING_2D); WM_manipulator_set_flag(man->translate_c, WM_MANIPULATOR_DRAW_VALUE, true); WM_manipulator_set_flag(man->rotate_c, WM_MANIPULATOR_DRAW_VALUE, true); diff --git a/source/blender/editors/mesh/editmesh_knife.c b/source/blender/editors/mesh/editmesh_knife.c index 3c974e4b3b9..433163b2fab 100644 --- a/source/blender/editors/mesh/editmesh_knife.c +++ b/source/blender/editors/mesh/editmesh_knife.c @@ -54,6 +54,8 @@ #include "BKE_editmesh_bvh.h" #include "BKE_report.h" +#include "DEG_depsgraph.h" + #include "GPU_immediate.h" #include "GPU_matrix.h" @@ -159,6 +161,7 @@ typedef struct KnifePosData { typedef struct KnifeTool_OpData { ARegion *ar; /* region that knifetool was activated in */ void *draw_handle; /* for drawing preview loop */ + EvaluationContext eval_ctx; ViewContext vc; /* note: _don't_ use 'mval', instead use the one we define below */ float mval[2]; /* mouse value with snapping applied */ //bContext *C; @@ -1226,6 +1229,7 @@ static bool knife_ray_intersect_face( for (; tri_i < tottri; tri_i++) { const float *lv1, *lv2, *lv3; + float ray_tri_uv[2]; tri = kcd->em->looptris[tri_i]; if (tri[0]->f != f) @@ -1237,7 +1241,7 @@ static bool knife_ray_intersect_face( * tesselation edge and might not hit either tesselation tri with * an exact test; * we will exclude hits near real edges by a later test */ - if (isect_ray_tri_epsilon_v3(v1, raydir, lv1, lv2, lv3, &lambda, NULL, KNIFE_FLT_EPS)) { + if (isect_ray_tri_epsilon_v3(v1, raydir, lv1, lv2, lv3, &lambda, ray_tri_uv, KNIFE_FLT_EPS)) { /* check if line coplanar with tri */ normal_tri_v3(tri_norm, lv1, lv2, lv3); plane_from_point_normal_v3(tri_plane, lv1, tri_norm); @@ -1246,8 +1250,7 @@ static bool knife_ray_intersect_face( { return false; } - copy_v3_v3(hit_cageco, v1); - madd_v3_v3fl(hit_cageco, raydir, lambda); + interp_v3_v3v3v3_uv(hit_cageco, lv1, lv2, lv3, ray_tri_uv); /* Now check that far enough away from verts and edges */ lst = knife_get_face_kedges(kcd, f); for (ref = lst->first; ref; ref = ref->next) { @@ -1259,11 +1262,7 @@ static bool knife_ray_intersect_face( return false; } } - - transform_point_by_tri_v3( - hit_co, hit_cageco, - tri[0]->v->co, tri[1]->v->co, tri[2]->v->co, - lv1, lv2, lv3); + interp_v3_v3v3v3_uv(hit_co, tri[0]->v->co, tri[1]->v->co, tri[2]->v->co, ray_tri_uv); return true; } } @@ -1837,7 +1836,7 @@ static BMFace *knife_find_closest_face(KnifeTool_OpData *kcd, float co[3], float if (!f) { if (kcd->is_interactive) { /* try to use backbuffer selection method if ray casting failed */ - f = EDBM_face_find_nearest(&kcd->vc, &dist); + f = EDBM_face_find_nearest(&kcd->eval_ctx, &kcd->vc, &dist); /* cheat for now; just put in the origin instead * of a true coordinate on the face. @@ -2589,7 +2588,7 @@ static void knifetool_init_bmbvh(KnifeTool_OpData *kcd) { BM_mesh_elem_index_ensure(kcd->em->bm, BM_VERT); - kcd->cagecos = (const float (*)[3])BKE_editmesh_vertexCos_get(kcd->em, kcd->scene, NULL); + kcd->cagecos = (const float (*)[3])BKE_editmesh_vertexCos_get(&kcd->eval_ctx, kcd->em, kcd->scene, NULL); kcd->bmbvh = BKE_bmbvh_new_from_editmesh( kcd->em, @@ -2623,6 +2622,7 @@ static void knifetool_init(bContext *C, KnifeTool_OpData *kcd, kcd->ob = obedit; kcd->ar = CTX_wm_region(C); + CTX_data_eval_ctx(C, &kcd->eval_ctx); em_setup_viewcontext(C, &kcd->vc); kcd->em = BKE_editmesh_from_object(kcd->ob); @@ -2777,6 +2777,7 @@ static int knifetool_modal(bContext *C, wmOperator *op, const wmEvent *event) return OPERATOR_FINISHED; } + CTX_data_eval_ctx(C, &kcd->eval_ctx); em_setup_viewcontext(C, &kcd->vc); kcd->ar = kcd->vc.ar; diff --git a/source/blender/editors/mesh/editmesh_knife_project.c b/source/blender/editors/mesh/editmesh_knife_project.c index 0d3cc07589b..c98d22503e1 100644 --- a/source/blender/editors/mesh/editmesh_knife_project.c +++ b/source/blender/editors/mesh/editmesh_knife_project.c @@ -42,6 +42,8 @@ #include "BKE_editmesh.h" #include "BKE_report.h" +#include "DEG_depsgraph.h" + #include "RNA_define.h" #include "RNA_access.h" @@ -56,13 +58,17 @@ #include "mesh_intern.h" /* own include */ -static LinkNode *knifeproject_poly_from_object(ARegion *ar, Scene *scene, Object *ob, LinkNode *polys) +static LinkNode *knifeproject_poly_from_object(const bContext *C, Scene *scene, Object *ob, LinkNode *polys) { + ARegion *ar = CTX_wm_region(C); + EvaluationContext eval_ctx; DerivedMesh *dm; bool dm_needsFree; + CTX_data_eval_ctx(C, &eval_ctx); + if (ob->type == OB_MESH || ob->derivedFinal) { - dm = ob->derivedFinal ? ob->derivedFinal : mesh_get_derived_final(scene, ob, CD_MASK_BAREMESH); + dm = ob->derivedFinal ? ob->derivedFinal : mesh_get_derived_final(&eval_ctx, scene, ob, CD_MASK_BAREMESH); dm_needsFree = false; } else if (ELEM(ob->type, OB_FONT, OB_CURVE, OB_SURF)) { @@ -116,7 +122,6 @@ static LinkNode *knifeproject_poly_from_object(ARegion *ar, Scene *scene, Object static int knifeproject_exec(bContext *C, wmOperator *op) { - ARegion *ar = CTX_wm_region(C); Scene *scene = CTX_data_scene(C); Object *obedit = CTX_data_edit_object(C); BMEditMesh *em = BKE_editmesh_from_object(obedit); @@ -127,7 +132,7 @@ static int knifeproject_exec(bContext *C, wmOperator *op) CTX_DATA_BEGIN (C, Object *, ob, selected_objects) { if (ob != obedit) { - polys = knifeproject_poly_from_object(ar, scene, ob, polys); + polys = knifeproject_poly_from_object(C, scene, ob, polys); } } CTX_DATA_END; diff --git a/source/blender/editors/mesh/editmesh_loopcut.c b/source/blender/editors/mesh/editmesh_loopcut.c index 6a656ace09c..a4a6ad82dfb 100644 --- a/source/blender/editors/mesh/editmesh_loopcut.c +++ b/source/blender/editors/mesh/editmesh_loopcut.c @@ -63,6 +63,8 @@ #include "WM_api.h" #include "WM_types.h" +#include "DEG_depsgraph.h" + #include "mesh_intern.h" /* own include */ #define SUBD_SMOOTH_MAX 4.0f @@ -556,20 +558,23 @@ static void loopcut_update_edge(RingSelOpData *lcd, BMEdge *e, const int preview } } -static void loopcut_mouse_move(RingSelOpData *lcd, const int previewlines) +static void loopcut_mouse_move(const struct EvaluationContext *eval_ctx, RingSelOpData *lcd, const int previewlines) { float dist = ED_view3d_select_dist_px(); - BMEdge *e = EDBM_edge_find_nearest(&lcd->vc, &dist); + BMEdge *e = EDBM_edge_find_nearest(eval_ctx, &lcd->vc, &dist); loopcut_update_edge(lcd, e, previewlines); } /* called by both init() and exec() */ static int loopcut_init(bContext *C, wmOperator *op, const wmEvent *event) { + EvaluationContext eval_ctx; const bool is_interactive = (event != NULL); Object *obedit = CTX_data_edit_object(C); RingSelOpData *lcd; + CTX_data_eval_ctx(C, &eval_ctx); + if (modifiers_isDeformedByLattice(obedit) || modifiers_isDeformedByArmature(obedit)) BKE_report(op->reports, RPT_WARNING, "Loop cut does not work well on deformed edit mesh display"); @@ -597,7 +602,7 @@ static int loopcut_init(bContext *C, wmOperator *op, const wmEvent *event) if (is_interactive) { copy_v2_v2_int(lcd->vc.mval, event->mval); - loopcut_mouse_move(lcd, is_interactive ? 1 : 0); + loopcut_mouse_move(&eval_ctx, lcd, is_interactive ? 1 : 0); } else { const int e_index = RNA_int_get(op->ptr, "edge_index"); @@ -670,12 +675,14 @@ static int loopcut_finish(RingSelOpData *lcd, bContext *C, wmOperator *op) static int loopcut_modal(bContext *C, wmOperator *op, const wmEvent *event) { + EvaluationContext eval_ctx; RingSelOpData *lcd = op->customdata; float cuts = lcd->cuts; float smoothness = lcd->smoothness; bool show_cuts = false; const bool has_numinput = hasNumInput(&lcd->num); + CTX_data_eval_ctx(C, &eval_ctx); em_setup_viewcontext(C, &lcd->vc); lcd->ar = lcd->vc.ar; @@ -761,7 +768,7 @@ static int loopcut_modal(bContext *C, wmOperator *op, const wmEvent *event) if (!has_numinput) { lcd->vc.mval[0] = event->mval[0]; lcd->vc.mval[1] = event->mval[1]; - loopcut_mouse_move(lcd, (int)lcd->cuts); + loopcut_mouse_move(&eval_ctx, lcd, (int)lcd->cuts); ED_region_tag_redraw(lcd->ar); handled = true; diff --git a/source/blender/editors/mesh/editmesh_path.c b/source/blender/editors/mesh/editmesh_path.c index 4431712e720..29bca00f1a9 100644 --- a/source/blender/editors/mesh/editmesh_path.c +++ b/source/blender/editors/mesh/editmesh_path.c @@ -59,6 +59,8 @@ #include "bmesh.h" #include "bmesh_tools.h" +#include "DEG_depsgraph.h" + #include "mesh_intern.h" /* own include */ struct PathSelectParams { @@ -570,19 +572,19 @@ static bool edbm_shortest_path_pick_ex( static int edbm_shortest_path_pick_exec(bContext *C, wmOperator *op); -static BMElem *edbm_elem_find_nearest(ViewContext *vc, const char htype) +static BMElem *edbm_elem_find_nearest(const struct EvaluationContext *eval_ctx, ViewContext *vc, const char htype) { BMEditMesh *em = vc->em; float dist = ED_view3d_select_dist_px(); if ((em->selectmode & SCE_SELECT_VERTEX) && (htype == BM_VERT)) { - return (BMElem *)EDBM_vert_find_nearest(vc, &dist); + return (BMElem *)EDBM_vert_find_nearest(eval_ctx, vc, &dist); } else if ((em->selectmode & SCE_SELECT_EDGE) && (htype == BM_EDGE)) { - return (BMElem *)EDBM_edge_find_nearest(vc, &dist); + return (BMElem *)EDBM_edge_find_nearest(eval_ctx, vc, &dist); } else if ((em->selectmode & SCE_SELECT_FACE) && (htype == BM_FACE)) { - return (BMElem *)EDBM_face_find_nearest(vc, &dist); + return (BMElem *)EDBM_face_find_nearest(eval_ctx, vc, &dist); } return NULL; @@ -605,10 +607,12 @@ static int edbm_shortest_path_pick_invoke(bContext *C, wmOperator *op, const wmE return edbm_shortest_path_pick_exec(C, op); } + EvaluationContext eval_ctx; ViewContext vc; BMEditMesh *em; bool track_active = true; + CTX_data_eval_ctx(C, &eval_ctx); em_setup_viewcontext(C, &vc); copy_v2_v2_int(vc.mval, event->mval); em = vc.em; @@ -617,14 +621,14 @@ static int edbm_shortest_path_pick_invoke(bContext *C, wmOperator *op, const wmE BMElem *ele_src, *ele_dst; if (!(ele_src = edbm_elem_active_elem_or_face_get(em->bm)) || - !(ele_dst = edbm_elem_find_nearest(&vc, ele_src->head.htype))) + !(ele_dst = edbm_elem_find_nearest(&eval_ctx, &vc, ele_src->head.htype))) { /* special case, toggle edge tags even when we don't have a path */ if (((em->selectmode & SCE_SELECT_EDGE) && (vc.scene->toolsettings->edge_mode != EDGE_MODE_SELECT)) && /* check if we only have a destination edge */ ((ele_src == NULL) && - (ele_dst = edbm_elem_find_nearest(&vc, BM_EDGE)))) + (ele_dst = edbm_elem_find_nearest(&eval_ctx, &vc, BM_EDGE)))) { ele_src = ele_dst; track_active = false; diff --git a/source/blender/editors/mesh/editmesh_select.c b/source/blender/editors/mesh/editmesh_select.c index 61891907050..7fe4e58d2e0 100644 --- a/source/blender/editors/mesh/editmesh_select.c +++ b/source/blender/editors/mesh/editmesh_select.c @@ -68,6 +68,8 @@ #include "bmesh_tools.h" +#include "DEG_depsgraph.h" + #include "mesh_intern.h" /* own include */ /* use bmesh operator flags for a few operators */ @@ -194,7 +196,9 @@ static BLI_bitmap *edbm_backbuf_alloc(const int size) /* reads rect, and builds selection array for quick lookup */ /* returns if all is OK */ -bool EDBM_backbuf_border_init(ViewContext *vc, short xmin, short ymin, short xmax, short ymax) +bool EDBM_backbuf_border_init( + const struct EvaluationContext *eval_ctx, ViewContext *vc, short xmin, + short ymin, short xmax, short ymax) { struct ImBuf *buf; unsigned int *dr; @@ -204,7 +208,7 @@ bool EDBM_backbuf_border_init(ViewContext *vc, short xmin, short ymin, short xma return false; } - buf = ED_view3d_backbuf_read(vc, xmin, ymin, xmax, ymax); + buf = ED_view3d_backbuf_read(eval_ctx, vc, xmin, ymin, xmax, ymax); if ((buf == NULL) || (bm_vertoffs == 0)) { return false; } @@ -267,7 +271,7 @@ static void edbm_mask_lasso_px_cb(int x, int x_end, int y, void *user_data) * - grab again and compare * returns 'OK' */ -bool EDBM_backbuf_border_mask_init(ViewContext *vc, const int mcords[][2], short tot, short xmin, short ymin, short xmax, short ymax) +bool EDBM_backbuf_border_mask_init(const struct EvaluationContext *eval_ctx, ViewContext *vc, const int mcords[][2], short tot, short xmin, short ymin, short xmax, short ymax) { unsigned int *dr, *dr_mask, *dr_mask_arr; struct ImBuf *buf; @@ -284,7 +288,7 @@ bool EDBM_backbuf_border_mask_init(ViewContext *vc, const int mcords[][2], short return false; } - buf = ED_view3d_backbuf_read(vc, xmin, ymin, xmax, ymax); + buf = ED_view3d_backbuf_read(eval_ctx, vc, xmin, ymin, xmax, ymax); if ((buf == NULL) || (bm_vertoffs == 0)) { return false; } @@ -317,7 +321,9 @@ bool EDBM_backbuf_border_mask_init(ViewContext *vc, const int mcords[][2], short } /* circle shaped sample area */ -bool EDBM_backbuf_circle_init(ViewContext *vc, short xs, short ys, short rads) +bool EDBM_backbuf_circle_init( + const struct EvaluationContext *eval_ctx, ViewContext *vc, + short xs, short ys, short rads) { struct ImBuf *buf; unsigned int *dr; @@ -336,7 +342,7 @@ bool EDBM_backbuf_circle_init(ViewContext *vc, short xs, short ys, short rads) xmin = xs - rads; xmax = xs + rads; ymin = ys - rads; ymax = ys + rads; - buf = ED_view3d_backbuf_read(vc, xmin, ymin, xmax, ymax); + buf = ED_view3d_backbuf_read(eval_ctx, vc, xmin, ymin, xmax, ymax); if ((buf == NULL) || (bm_vertoffs == 0)) { return false; } @@ -435,7 +441,7 @@ static void findnearestvert__doClosest(void *userData, BMVert *eve, const float * \param use_cycle Cycle over elements within #FIND_NEAR_CYCLE_THRESHOLD_MIN in order of index. */ BMVert *EDBM_vert_find_nearest_ex( - ViewContext *vc, float *r_dist, + const struct EvaluationContext *eval_ctx, ViewContext *vc, float *r_dist, const bool use_select_bias, bool use_cycle) { BMesh *bm = vc->em->bm; @@ -446,8 +452,11 @@ BMVert *EDBM_vert_find_nearest_ex( unsigned int index; BMVert *eve; + /* No afterqueue (yet), so we check it now, otherwise the bm_xxxofs indices are bad. */ + ED_view3d_backbuf_validate(eval_ctx, vc); + index = ED_view3d_backbuf_sample_rect( - vc, vc->mval, dist_px, bm_wireoffs, 0xFFFFFF, &dist_test); + eval_ctx, vc, vc->mval, dist_px, bm_wireoffs, 0xFFFFFF, &dist_test); eve = index ? BM_vert_at_index_find_or_table(bm, index - 1) : NULL; if (eve) { @@ -482,7 +491,7 @@ BMVert *EDBM_vert_find_nearest_ex( data.cycle_index_prev = prev_select_index; ED_view3d_init_mats_rv3d(vc->obedit, vc->rv3d); - mesh_foreachScreenVert(vc, findnearestvert__doClosest, &data, clip_flag); + mesh_foreachScreenVert(eval_ctx, vc, findnearestvert__doClosest, &data, clip_flag); hit = (data.use_cycle && data.hit_cycle.vert) ? &data.hit_cycle : &data.hit; *r_dist = hit->dist; @@ -494,9 +503,9 @@ BMVert *EDBM_vert_find_nearest_ex( } } -BMVert *EDBM_vert_find_nearest(ViewContext *vc, float *r_dist) +BMVert *EDBM_vert_find_nearest(const struct EvaluationContext *eval_ctx, ViewContext *vc, float *r_dist) { - return EDBM_vert_find_nearest_ex(vc, r_dist, false, false); + return EDBM_vert_find_nearest_ex(eval_ctx, vc, r_dist, false, false); } /* find the distance to the edge we already have */ @@ -618,7 +627,7 @@ static void find_nearest_edge__doClosest( } BMEdge *EDBM_edge_find_nearest_ex( - ViewContext *vc, float *r_dist, + const struct EvaluationContext *eval_ctx, ViewContext *vc, float *r_dist, float *r_dist_center, const bool use_select_bias, const bool use_cycle, BMEdge **r_eed_zbuf) @@ -630,10 +639,11 @@ BMEdge *EDBM_edge_find_nearest_ex( float dist_test = 0.0f; unsigned int index; BMEdge *eed; - - ED_view3d_backbuf_validate(vc); - index = ED_view3d_backbuf_sample_rect(vc, vc->mval, dist_px, bm_solidoffs, bm_wireoffs, &dist_test); + /* No afterqueue (yet), so we check it now, otherwise the bm_xxxofs indices are bad. */ + ED_view3d_backbuf_validate(eval_ctx, vc); + + index = ED_view3d_backbuf_sample_rect(eval_ctx, vc, vc->mval, dist_px, bm_solidoffs, bm_wireoffs, &dist_test); eed = index ? BM_edge_at_index_find_or_table(bm, index - 1) : NULL; if (r_eed_zbuf) { @@ -651,7 +661,7 @@ BMEdge *EDBM_edge_find_nearest_ex( ED_view3d_init_mats_rv3d(vc->obedit, vc->rv3d); - mesh_foreachScreenEdge(vc, find_nearest_edge_center__doZBuf, &data, V3D_PROJ_TEST_CLIP_DEFAULT); + mesh_foreachScreenEdge(eval_ctx, vc, find_nearest_edge_center__doZBuf, &data, V3D_PROJ_TEST_CLIP_DEFAULT); *r_dist_center = data.dist; } @@ -691,7 +701,7 @@ BMEdge *EDBM_edge_find_nearest_ex( data.cycle_index_prev = prev_select_index; ED_view3d_init_mats_rv3d(vc->obedit, vc->rv3d); - mesh_foreachScreenEdge(vc, find_nearest_edge__doClosest, &data, clip_flag); + mesh_foreachScreenEdge(eval_ctx, vc, find_nearest_edge__doClosest, &data, clip_flag); hit = (data.use_cycle && data.hit_cycle.edge) ? &data.hit_cycle : &data.hit; *r_dist = hit->dist; @@ -707,9 +717,9 @@ BMEdge *EDBM_edge_find_nearest_ex( } BMEdge *EDBM_edge_find_nearest( - ViewContext *vc, float *r_dist) + const struct EvaluationContext *eval_ctx, ViewContext *vc, float *r_dist) { - return EDBM_edge_find_nearest_ex(vc, r_dist, NULL, false, false, NULL); + return EDBM_edge_find_nearest_ex(eval_ctx, vc, r_dist, NULL, false, false, NULL); } /* find the distance to the face we already have */ @@ -783,7 +793,7 @@ static void findnearestface__doClosest(void *userData, BMFace *efa, const float BMFace *EDBM_face_find_nearest_ex( - ViewContext *vc, float *r_dist, + const struct EvaluationContext *eval_ctx, ViewContext *vc, float *r_dist, float *r_dist_center, const bool use_select_bias, const bool use_cycle, BMFace **r_efa_zbuf) @@ -795,9 +805,9 @@ BMFace *EDBM_face_find_nearest_ex( unsigned int index; BMFace *efa; - ED_view3d_backbuf_validate(vc); + ED_view3d_backbuf_validate(eval_ctx, vc); - index = ED_view3d_backbuf_sample(vc, vc->mval[0], vc->mval[1]); + index = ED_view3d_backbuf_sample(eval_ctx, vc, vc->mval[0], vc->mval[1]); efa = index ? BM_face_at_index_find_or_table(bm, index - 1) : NULL; if (r_efa_zbuf) { @@ -815,7 +825,7 @@ BMFace *EDBM_face_find_nearest_ex( ED_view3d_init_mats_rv3d(vc->obedit, vc->rv3d); - mesh_foreachScreenFace(vc, find_nearest_face_center__doZBuf, &data, V3D_PROJ_TEST_CLIP_DEFAULT); + mesh_foreachScreenFace(eval_ctx, vc, find_nearest_face_center__doZBuf, &data, V3D_PROJ_TEST_CLIP_DEFAULT); *r_dist_center = data.dist; } @@ -853,7 +863,7 @@ BMFace *EDBM_face_find_nearest_ex( data.cycle_index_prev = prev_select_index; ED_view3d_init_mats_rv3d(vc->obedit, vc->rv3d); - mesh_foreachScreenFace(vc, findnearestface__doClosest, &data, clip_flag); + mesh_foreachScreenFace(eval_ctx, vc, findnearestface__doClosest, &data, clip_flag); hit = (data.use_cycle && data.hit_cycle.face) ? &data.hit_cycle : &data.hit; *r_dist = hit->dist; @@ -868,9 +878,9 @@ BMFace *EDBM_face_find_nearest_ex( } } -BMFace *EDBM_face_find_nearest(ViewContext *vc, float *r_dist) +BMFace *EDBM_face_find_nearest(const struct EvaluationContext *eval_ctx, ViewContext *vc, float *r_dist) { - return EDBM_face_find_nearest_ex(vc, r_dist, NULL, false, false, NULL); + return EDBM_face_find_nearest_ex(eval_ctx, vc, r_dist, NULL, false, false, NULL); } #undef FIND_NEAR_SELECT_BIAS @@ -882,7 +892,9 @@ BMFace *EDBM_face_find_nearest(ViewContext *vc, float *r_dist) * selected vertices and edges get disadvantage * return 1 if found one */ -static int unified_findnearest(ViewContext *vc, BMVert **r_eve, BMEdge **r_eed, BMFace **r_efa) +static int unified_findnearest( + const struct EvaluationContext *eval_ctx, ViewContext *vc, + BMVert **r_eve, BMEdge **r_eed, BMFace **r_efa) { BMEditMesh *em = vc->em; static short mval_prev[2] = {-1, -1}; @@ -901,12 +913,12 @@ static int unified_findnearest(ViewContext *vc, BMVert **r_eve, BMEdge **r_eed, /* no afterqueue (yet), so we check it now, otherwise the em_xxxofs indices are bad */ - ED_view3d_backbuf_validate(vc); + ED_view3d_backbuf_validate(eval_ctx, vc); if ((dist > 0.0f) && em->selectmode & SCE_SELECT_FACE) { float dist_center = 0.0f; float *dist_center_p = (em->selectmode & (SCE_SELECT_EDGE | SCE_SELECT_VERTEX)) ? &dist_center : NULL; - efa = EDBM_face_find_nearest_ex(vc, &dist, dist_center_p, true, use_cycle, &efa_zbuf); + efa = EDBM_face_find_nearest_ex(eval_ctx, vc, &dist, dist_center_p, true, use_cycle, &efa_zbuf); if (efa && dist_center_p) { dist = min_ff(dist_margin, dist_center); } @@ -915,14 +927,14 @@ static int unified_findnearest(ViewContext *vc, BMVert **r_eve, BMEdge **r_eed, if ((dist > 0.0f) && (em->selectmode & SCE_SELECT_EDGE)) { float dist_center = 0.0f; float *dist_center_p = (em->selectmode & SCE_SELECT_VERTEX) ? &dist_center : NULL; - eed = EDBM_edge_find_nearest_ex(vc, &dist, dist_center_p, true, use_cycle, &eed_zbuf); + eed = EDBM_edge_find_nearest_ex(eval_ctx, vc, &dist, dist_center_p, true, use_cycle, &eed_zbuf); if (eed && dist_center_p) { dist = min_ff(dist_margin, dist_center); } } if ((dist > 0.0f) && em->selectmode & SCE_SELECT_VERTEX) { - eve = EDBM_vert_find_nearest_ex(vc, &dist, true, use_cycle); + eve = EDBM_vert_find_nearest_ex(eval_ctx, vc, &dist, true, use_cycle); } /* return only one of 3 pointers, for frontbuffer redraws */ @@ -1555,6 +1567,7 @@ static void mouse_mesh_loop_edge(BMEditMesh *em, BMEdge *eed, bool select, bool static bool mouse_mesh_loop(bContext *C, const int mval[2], bool extend, bool deselect, bool toggle, bool ring) { + EvaluationContext eval_ctx; ViewContext vc; BMEditMesh *em; BMEdge *eed; @@ -1564,15 +1577,16 @@ static bool mouse_mesh_loop(bContext *C, const int mval[2], bool extend, bool de float dist = ED_view3d_select_dist_px() * 0.6666f; float mvalf[2]; + CTX_data_eval_ctx(C, &eval_ctx); em_setup_viewcontext(C, &vc); mvalf[0] = (float)(vc.mval[0] = mval[0]); mvalf[1] = (float)(vc.mval[1] = mval[1]); em = vc.em; /* no afterqueue (yet), so we check it now, otherwise the bm_xxxofs indices are bad */ - ED_view3d_backbuf_validate(&vc); + ED_view3d_backbuf_validate(&eval_ctx, &vc); - eed = EDBM_edge_find_nearest_ex(&vc, &dist, NULL, true, true, NULL); + eed = EDBM_edge_find_nearest_ex(&eval_ctx, &vc, &dist, NULL, true, true, NULL); if (eed == NULL) { return false; } @@ -1815,17 +1829,19 @@ void MESH_OT_select_interior_faces(wmOperatorType *ot) /* gets called via generic mouse select operator */ bool EDBM_select_pick(bContext *C, const int mval[2], bool extend, bool deselect, bool toggle) { + EvaluationContext eval_ctx; ViewContext vc; BMVert *eve = NULL; BMEdge *eed = NULL; BMFace *efa = NULL; /* setup view context for argument to callbacks */ + CTX_data_eval_ctx(C, &eval_ctx); em_setup_viewcontext(C, &vc); vc.mval[0] = mval[0]; vc.mval[1] = mval[1]; - if (unified_findnearest(&vc, &eve, &eed, &efa)) { + if (unified_findnearest(&eval_ctx, &vc, &eve, &eed, &efa)) { /* Deselect everything */ if (extend == false && deselect == false && toggle == false) @@ -1912,12 +1928,30 @@ bool EDBM_select_pick(bContext *C, const int mval[2], bool extend, bool deselect EDBM_selectmode_flush(vc.em); - /* change active material on object */ - if (efa && efa->mat_nr != vc.obedit->actcol - 1) { - vc.obedit->actcol = efa->mat_nr + 1; - vc.em->mat_nr = efa->mat_nr; + if (efa) { + /* Change active material on object. */ + if (efa->mat_nr != vc.obedit->actcol - 1) { + vc.obedit->actcol = efa->mat_nr + 1; + vc.em->mat_nr = efa->mat_nr; + WM_event_add_notifier(C, NC_MATERIAL | ND_SHADING_LINKS, NULL); + } - WM_event_add_notifier(C, NC_MATERIAL | ND_SHADING_LINKS, NULL); + /* Change active face-map on object. */ + if (!BLI_listbase_is_empty(&vc.obedit->fmaps)) { + const int cd_fmap_offset = CustomData_get_offset(&vc.em->bm->pdata, CD_FACEMAP); + if (cd_fmap_offset != -1) { + int map = *((int *)BM_ELEM_CD_GET_VOID_P(efa, cd_fmap_offset)); + if ((map < -1) || (map > BLI_listbase_count_ex(&vc.obedit->fmaps, map))) { + map = -1; + } + map += 1; + if (map != vc.obedit->actfmap) { + /* We may want to add notifiers later, + * currently select update handles redraw. */ + vc.obedit->actfmap = map; + } + } + } } @@ -2771,6 +2805,7 @@ static void edbm_select_linked_pick_ex(BMEditMesh *em, BMElem *ele, bool sel, in static int edbm_select_linked_pick_invoke(bContext *C, wmOperator *op, const wmEvent *event) { Object *obedit = CTX_data_edit_object(C); + EvaluationContext eval_ctx; ViewContext vc; BMEditMesh *em; BMesh *bm; @@ -2788,6 +2823,7 @@ static int edbm_select_linked_pick_invoke(bContext *C, wmOperator *op, const wmE view3d_operator_needs_opengl(C); /* setup view context for argument to callbacks */ + CTX_data_eval_ctx(C, &eval_ctx); em_setup_viewcontext(C, &vc); em = vc.em; bm = em->bm; @@ -2800,7 +2836,7 @@ static int edbm_select_linked_pick_invoke(bContext *C, wmOperator *op, const wmE vc.mval[1] = event->mval[1]; /* return warning! */ - if (unified_findnearest(&vc, &eve, &eed, &efa) == 0) { + if (unified_findnearest(&eval_ctx, &vc, &eve, &eed, &efa) == 0) { WM_event_add_notifier(C, NC_GEOM | ND_SELECT, obedit); return OPERATOR_CANCELLED; diff --git a/source/blender/editors/mesh/editmesh_tools.c b/source/blender/editors/mesh/editmesh_tools.c index cbed6a37c1f..b2a16d9373b 100644 --- a/source/blender/editors/mesh/editmesh_tools.c +++ b/source/blender/editors/mesh/editmesh_tools.c @@ -172,7 +172,7 @@ struct EdgeRingOpSubdProps { }; -static void mesh_operator_edgering_props(wmOperatorType *ot, const int cuts_default) +static void mesh_operator_edgering_props(wmOperatorType *ot, const int cuts_min, const int cuts_default) { /* Note, these values must match delete_mesh() event values */ static EnumPropertyItem prop_subd_edgering_types[] = { @@ -184,7 +184,7 @@ static void mesh_operator_edgering_props(wmOperatorType *ot, const int cuts_defa PropertyRNA *prop; - prop = RNA_def_int(ot->srna, "number_cuts", cuts_default, 0, 1000, "Number of Cuts", "", 0, 64); + prop = RNA_def_int(ot->srna, "number_cuts", cuts_default, 0, 1000, "Number of Cuts", "", cuts_min, 64); RNA_def_property_flag(prop, PROP_SKIP_SAVE); RNA_def_enum(ot->srna, "interpolation", prop_subd_edgering_types, SUBD_RING_INTERP_PATH, @@ -251,7 +251,7 @@ void MESH_OT_subdivide_edgering(wmOperatorType *ot) ot->flag = OPTYPE_REGISTER | OPTYPE_UNDO; /* properties */ - mesh_operator_edgering_props(ot, 10); + mesh_operator_edgering_props(ot, 1, 10); } @@ -3303,13 +3303,13 @@ static int edbm_separate_exec(bContext *C, wmOperator *op) /* editmode separate */ switch (type) { case MESH_SEPARATE_SELECTED: - retval = mesh_separate_selected(bmain, scene, sl, base, em->bm); + retval = mesh_separate_selected(bmain, scene, sl, base, em->bm); break; case MESH_SEPARATE_MATERIAL: - retval = mesh_separate_material(bmain, scene, sl, base, em->bm); + retval = mesh_separate_material(bmain, scene, sl, base, em->bm); break; case MESH_SEPARATE_LOOSE: - retval = mesh_separate_loose(bmain, scene, sl, base, em->bm); + retval = mesh_separate_loose(bmain, scene, sl, base, em->bm); break; default: BLI_assert(0); @@ -3344,10 +3344,10 @@ static int edbm_separate_exec(bContext *C, wmOperator *op) switch (type) { case MESH_SEPARATE_MATERIAL: - retval_iter = mesh_separate_material(bmain, scene, sl, base_iter, bm_old); + retval_iter = mesh_separate_material(bmain, scene, sl, base_iter, bm_old); break; case MESH_SEPARATE_LOOSE: - retval_iter = mesh_separate_loose(bmain, scene, sl, base_iter, bm_old); + retval_iter = mesh_separate_loose(bmain, scene, sl, base_iter, bm_old); break; default: BLI_assert(0); @@ -5063,7 +5063,7 @@ static void sort_bmelem_flag(Scene *scene, Object *ob, } BM_mesh_remap(em->bm, map[0], map[1], map[2]); -/* DAG_id_tag_update(ob->data, 0);*/ +/* DEG_id_tag_update(ob->data, 0);*/ for (j = 3; j--; ) { if (map[j]) @@ -5451,7 +5451,7 @@ void MESH_OT_bridge_edge_loops(wmOperatorType *ot) RNA_def_float(ot->srna, "merge_factor", 0.5f, 0.0f, 1.0f, "Merge Factor", "", 0.0f, 1.0f); RNA_def_int(ot->srna, "twist_offset", 0, -1000, 1000, "Twist", "Twist offset for closed loops", -1000, 1000); - mesh_operator_edgering_props(ot, 0); + mesh_operator_edgering_props(ot, 0, 0); } static int edbm_wireframe_exec(bContext *C, wmOperator *op) diff --git a/source/blender/editors/mesh/editmesh_utils.c b/source/blender/editors/mesh/editmesh_utils.c index 555fe6c917d..f24b7911e34 100644 --- a/source/blender/editors/mesh/editmesh_utils.c +++ b/source/blender/editors/mesh/editmesh_utils.c @@ -383,7 +383,7 @@ void EDBM_mesh_make(ToolSettings *ts, Object *ob, const bool add_key_index) /** * \warning This can invalidate the #DerivedMesh cache of other objects (for linked duplicates). - * Most callers should run #DAG_id_tag_update on \a ob->data, see: T46738, T46913 + * Most callers should run #DEG_id_tag_update on \a ob->data, see: T46738, T46913 */ void EDBM_mesh_load(Object *ob) { diff --git a/source/blender/editors/mesh/mesh_data.c b/source/blender/editors/mesh/mesh_data.c index 49755c75480..f2e60c55574 100644 --- a/source/blender/editors/mesh/mesh_data.c +++ b/source/blender/editors/mesh/mesh_data.c @@ -253,7 +253,7 @@ void ED_mesh_uv_loop_reset(struct bContext *C, struct Mesh *me) { /* could be ldata or pdata */ CustomData *ldata = GET_CD_DATA(me, ldata); - const int layernum = CustomData_get_active_layer_index(ldata, CD_MLOOPUV); + const int layernum = CustomData_get_active_layer(ldata, CD_MLOOPUV); ED_mesh_uv_loop_reset_ex(me, layernum); WM_event_add_notifier(C, NC_GEOM | ND_DATA, me); @@ -440,6 +440,20 @@ int ED_mesh_color_add(Mesh *me, const char *name, const bool active_set) return layernum; } +bool ED_mesh_color_ensure(struct Mesh *me, const char *name) +{ + BLI_assert(me->edit_btmesh == NULL); + + if (!me->mloopcol && me->totloop) { + CustomData_add_layer_named(&me->ldata, CD_MLOOPCOL, CD_DEFAULT, NULL, me->totloop, name); + BKE_mesh_update_customdata_pointers(me, true); + } + + DEG_id_tag_update(&me->id, 0); + + return (me->mloopcol != NULL); +} + bool ED_mesh_color_remove_index(Mesh *me, const int n) { CustomData *ldata = GET_CD_DATA(me, ldata); diff --git a/source/blender/editors/mesh/mesh_navmesh.c b/source/blender/editors/mesh/mesh_navmesh.c index 66c77593c75..e5705d2d3e7 100644 --- a/source/blender/editors/mesh/mesh_navmesh.c +++ b/source/blender/editors/mesh/mesh_navmesh.c @@ -73,18 +73,21 @@ static void createVertsTrisData(bContext *C, LinkNode *obs, LinkNode *oblink, *dmlink; DerivedMesh *dm; Scene *scene = CTX_data_scene(C); + EvaluationContext eval_ctx; LinkNode *dms = NULL; int nverts, ntris, *tris; float *verts; + CTX_data_eval_ctx(C, &eval_ctx); + nverts = 0; ntris = 0; /* calculate number of verts and tris */ for (oblink = obs; oblink; oblink = oblink->next) { ob = (Object *) oblink->link; - dm = mesh_create_derived_no_virtual(scene, ob, NULL, CD_MASK_MESH); + dm = mesh_create_derived_no_virtual(&eval_ctx, scene, ob, NULL, CD_MASK_MESH); DM_ensure_tessface(dm); BLI_linklist_prepend(&dms, dm); diff --git a/source/blender/editors/mesh/meshtools.c b/source/blender/editors/mesh/meshtools.c index e7b1f925d5e..da0da05bb13 100644 --- a/source/blender/editors/mesh/meshtools.c +++ b/source/blender/editors/mesh/meshtools.c @@ -79,8 +79,8 @@ * return 0 if no join is made (error) and 1 if the join is done */ static void join_mesh_single( - Main *bmain, Scene *scene, - Object *ob_dst, Base *base_src, float imat[4][4], + bContext *C, Main *bmain, Scene *scene, + Object *ob_dst, Object *ob_src, float imat[4][4], MVert **mvert_pp, MEdge **medge_pp, MLoop **mloop_pp, MPoly **mpoly_pp, CustomData *vdata, CustomData *edata, CustomData *ldata, CustomData *pdata, int totvert, int totedge, int totloop, int totpoly, @@ -88,14 +88,17 @@ static void join_mesh_single( Material **matar, int *matmap, int totcol, int *vertofs, int *edgeofs, int *loopofs, int *polyofs) { + EvaluationContext eval_ctx; int a, b; - Mesh *me = base_src->object->data; + Mesh *me = ob_src->data; MVert *mvert = *mvert_pp; MEdge *medge = *medge_pp; MLoop *mloop = *mloop_pp; MPoly *mpoly = *mpoly_pp; + CTX_data_eval_ctx(C, &eval_ctx); + if (me->totvert) { /* merge customdata flag */ ((Mesh *)ob_dst->data)->cd_flag |= me->cd_flag; @@ -114,10 +117,10 @@ static void join_mesh_single( /* Build src to merged mapping of vgroup indices. */ bDeformGroup *dg_src; - int *vgroup_index_map = alloca(sizeof(*vgroup_index_map) * BLI_listbase_count(&base_src->object->defbase)); + int *vgroup_index_map = alloca(sizeof(*vgroup_index_map) * BLI_listbase_count(&ob_src->defbase)); bool is_vgroup_remap_needed = false; - for (dg_src = base_src->object->defbase.first, b = 0; dg_src; dg_src = dg_src->next, b++) { + for (dg_src = ob_src->defbase.first, b = 0; dg_src; dg_src = dg_src->next, b++) { vgroup_index_map[b] = defgroup_name_index(ob_dst, dg_src->name); is_vgroup_remap_needed = is_vgroup_remap_needed || (vgroup_index_map[b] != b); } @@ -132,11 +135,11 @@ static void join_mesh_single( } /* if this is the object we're merging into, no need to do anything */ - if (base_src->object != ob_dst) { + if (ob_src != ob_dst) { float cmat[4][4]; /* watch this: switch matmul order really goes wrong */ - mul_m4_m4m4(cmat, imat, base_src->object->obmat); + mul_m4_m4m4(cmat, imat, ob_src->obmat); /* transform vertex coordinates into new space */ for (a = 0, mvert = *mvert_pp; a < me->totvert; a++, mvert++) { @@ -213,13 +216,13 @@ static void join_mesh_single( } if (me->totloop) { - if (base_src->object != ob_dst) { + if (ob_src != ob_dst) { MultiresModifierData *mmd; - multiresModifier_prepare_join(scene, base_src->object, ob_dst); + multiresModifier_prepare_join(&eval_ctx, scene, ob_src, ob_dst); - if ((mmd = get_multires_modifier(scene, base_src->object, true))) { - ED_object_iter_other(bmain, base_src->object, true, + if ((mmd = get_multires_modifier(scene, ob_src, true))) { + ED_object_iter_other(bmain, ob_src, true, ED_object_multires_update_totlevels_cb, &mmd->totlvl); } @@ -237,8 +240,8 @@ static void join_mesh_single( if (me->totpoly) { if (matmap) { /* make mapping for materials */ - for (a = 1; a <= base_src->object->totcol; a++) { - Material *ma = give_current_material(base_src->object, a); + for (a = 1; a <= ob_src->totcol; a++) { + Material *ma = give_current_material(ob_src, a); for (b = 0; b < totcol; b++) { if (ma == matar[b]) { @@ -273,8 +276,7 @@ int join_mesh_exec(bContext *C, wmOperator *op) { Main *bmain = CTX_data_main(C); Scene *scene = CTX_data_scene(C); - Base *ob_base = CTX_data_active_base(C); - Object *ob = ob_base->object; + Object *ob = CTX_data_active_object(C); Material **matar = NULL, *ma; Mesh *me; MVert *mvert = NULL; @@ -451,15 +453,6 @@ int join_mesh_exec(bContext *C, wmOperator *op) /* adjust settings to fit (allocate a new data-array) */ kbn->data = MEM_callocN(sizeof(float) * 3 * totvert, "joined_shapekey"); kbn->totelem = totvert; - - /* XXX 2.5 Animato */ -#if 0 - /* also, copy corresponding ipo-curve to ipo-block if applicable */ - if (me->key->ipo && key->ipo) { - /* FIXME... this is a luxury item! */ - puts("FIXME: ignoring IPO's when joining shapekeys on Meshes for now..."); - } -#endif } kb_map[i] = kbn; @@ -505,8 +498,8 @@ int join_mesh_exec(bContext *C, wmOperator *op) * active mesh will remain first ones in new result of the merge, in same order for CD layers, etc. See also T50084. */ join_mesh_single( - bmain, scene, - ob, ob_base, imat, + C, bmain, scene, + ob, ob, imat, &mvert, &medge, &mloop, &mpoly, &vdata, &edata, &ldata, &pdata, totvert, totedge, totloop, totpoly, @@ -522,8 +515,8 @@ int join_mesh_exec(bContext *C, wmOperator *op) /* only join if this is a mesh */ if (base->object->type == OB_MESH) { join_mesh_single( - bmain, scene, - ob, base, imat, + C, bmain, scene, + ob, base->object, imat, &mvert, &medge, &mloop, &mpoly, &vdata, &edata, &ldata, &pdata, totvert, totedge, totloop, totpoly, @@ -624,6 +617,7 @@ int join_mesh_shapes_exec(bContext *C, wmOperator *op) { Scene *scene = CTX_data_scene(C); Object *ob = CTX_data_active_object(C); + EvaluationContext eval_ctx; Mesh *me = (Mesh *)ob->data; Mesh *selme = NULL; DerivedMesh *dm = NULL; @@ -631,6 +625,8 @@ int join_mesh_shapes_exec(bContext *C, wmOperator *op) KeyBlock *kb; bool ok = false, nonequal_verts = false; + CTX_data_eval_ctx(C, &eval_ctx); + CTX_DATA_BEGIN (C, Base *, base, selected_editable_bases) { if (base->object == ob) continue; @@ -672,7 +668,7 @@ int join_mesh_shapes_exec(bContext *C, wmOperator *op) selme = (Mesh *)base->object->data; if (selme->totvert == me->totvert) { - dm = mesh_get_derived_deform(scene, base->object, CD_MASK_BAREMESH); + dm = mesh_get_derived_deform(&eval_ctx, scene, base->object, CD_MASK_BAREMESH); if (!dm) continue; @@ -1100,6 +1096,7 @@ int *mesh_get_x_mirror_faces(Object *ob, BMEditMesh *em, DerivedMesh *dm) */ bool ED_mesh_pick_face(bContext *C, Object *ob, const int mval[2], unsigned int *index, int size) { + EvaluationContext eval_ctx; ViewContext vc; Mesh *me = ob->data; @@ -1108,6 +1105,7 @@ bool ED_mesh_pick_face(bContext *C, Object *ob, const int mval[2], unsigned int if (!me || me->totpoly == 0) return false; + CTX_data_eval_ctx(C, &eval_ctx); view3d_set_viewcontext(C, &vc); if (size) { @@ -1115,11 +1113,11 @@ bool ED_mesh_pick_face(bContext *C, Object *ob, const int mval[2], unsigned int * on an edge in the backbuf, we can still select a face */ float dummy_dist; - *index = ED_view3d_backbuf_sample_rect(&vc, mval, size, 1, me->totpoly + 1, &dummy_dist); + *index = ED_view3d_backbuf_sample_rect(&eval_ctx, &vc, mval, size, 1, me->totpoly + 1, &dummy_dist); } else { /* sample only on the exact position */ - *index = ED_view3d_backbuf_sample(&vc, mval[0], mval[1]); + *index = ED_view3d_backbuf_sample(&eval_ctx, &vc, mval[0], mval[1]); } if ((*index) == 0 || (*index) > (unsigned int)me->totpoly) @@ -1158,9 +1156,12 @@ static void ed_mesh_pick_face_vert__mpoly_find( */ bool ED_mesh_pick_face_vert(bContext *C, Object *ob, const int mval[2], unsigned int *index, int size) { + EvaluationContext eval_ctx; unsigned int poly_index; Mesh *me = ob->data; + CTX_data_eval_ctx(C, &eval_ctx); + BLI_assert(me && GS(me->id.name) == ID_ME); if (ED_mesh_pick_face(C, ob, mval, &poly_index, size)) { @@ -1168,7 +1169,7 @@ bool ED_mesh_pick_face_vert(bContext *C, Object *ob, const int mval[2], unsigned struct ARegion *ar = CTX_wm_region(C); /* derived mesh to find deformed locations */ - DerivedMesh *dm = mesh_get_derived_final(scene, ob, CD_MASK_BAREMESH | CD_MASK_ORIGINDEX); + DerivedMesh *dm = mesh_get_derived_final(&eval_ctx, scene, ob, CD_MASK_BAREMESH | CD_MASK_ORIGINDEX); int v_idx_best = ORIGINDEX_NONE; @@ -1265,9 +1266,12 @@ static void ed_mesh_pick_vert__mapFunc(void *userData, int index, const float co } bool ED_mesh_pick_vert(bContext *C, Object *ob, const int mval[2], unsigned int *index, int size, bool use_zbuf) { + EvaluationContext eval_ctx; ViewContext vc; Mesh *me = ob->data; + CTX_data_eval_ctx(C, &eval_ctx); + BLI_assert(me && GS(me->id.name) == ID_ME); if (!me || me->totvert == 0) @@ -1281,11 +1285,11 @@ bool ED_mesh_pick_vert(bContext *C, Object *ob, const int mval[2], unsigned int * on an face in the backbuf, we can still select a vert */ float dummy_dist; - *index = ED_view3d_backbuf_sample_rect(&vc, mval, size, 1, me->totvert + 1, &dummy_dist); + *index = ED_view3d_backbuf_sample_rect(&eval_ctx, &vc, mval, size, 1, me->totvert + 1, &dummy_dist); } else { /* sample only on the exact position */ - *index = ED_view3d_backbuf_sample(&vc, mval[0], mval[1]); + *index = ED_view3d_backbuf_sample(&eval_ctx, &vc, mval[0], mval[1]); } if ((*index) == 0 || (*index) > (unsigned int)me->totvert) @@ -1295,7 +1299,7 @@ bool ED_mesh_pick_vert(bContext *C, Object *ob, const int mval[2], unsigned int } else { /* derived mesh to find deformed locations */ - DerivedMesh *dm = mesh_get_derived_final(vc.scene, ob, CD_MASK_BAREMESH); + DerivedMesh *dm = mesh_get_derived_final(&eval_ctx, vc.scene, ob, CD_MASK_BAREMESH); ARegion *ar = vc.ar; RegionView3D *rv3d = ar->regiondata; |