Welcome to mirror list, hosted at ThFree Co, Russian Federation.

git.blender.org/blender.git - Unnamed repository; edit this file 'description' to name the repository.
summaryrefslogtreecommitdiff
diff options
context:
space:
mode:
Diffstat (limited to 'source/blender/editors/mesh/editmesh_path.c')
-rw-r--r--source/blender/editors/mesh/editmesh_path.c144
1 files changed, 83 insertions, 61 deletions
diff --git a/source/blender/editors/mesh/editmesh_path.c b/source/blender/editors/mesh/editmesh_path.c
index eccc15bf83f..68157dab4e0 100644
--- a/source/blender/editors/mesh/editmesh_path.c
+++ b/source/blender/editors/mesh/editmesh_path.c
@@ -29,6 +29,8 @@
* \ingroup edmesh
*/
+#include "MEM_guardedalloc.h"
+
#include "DNA_scene_types.h"
#include "DNA_object_types.h"
#include "DNA_mesh_types.h"
@@ -41,6 +43,7 @@
#include "BLI_math.h"
#include "BLI_linklist.h"
+#include "BKE_layer.h"
#include "BKE_context.h"
#include "BKE_editmesh.h"
#include "BKE_report.h"
@@ -59,6 +62,8 @@
#include "bmesh.h"
#include "bmesh_tools.h"
+#include "DEG_depsgraph.h"
+
#include "mesh_intern.h" /* own include */
/* -------------------------------------------------------------------- */
@@ -126,10 +131,9 @@ static void verttag_set_cb(BMVert *v, bool val, void *user_data_v)
}
static void mouse_mesh_shortest_path_vert(
- Scene *scene, const struct PathSelectParams *op_params,
+ Scene *UNUSED(scene), Object *obedit, const struct PathSelectParams *op_params,
BMVert *v_act, BMVert *v_dst)
{
- Object *obedit = scene->obedit;
BMEditMesh *em = BKE_editmesh_from_object(obedit);
BMesh *bm = em->bm;
@@ -287,11 +291,11 @@ static void edgetag_set_cb(BMEdge *e, bool val, void *user_data_v)
}
}
-static void edgetag_ensure_cd_flag(Scene *scene, Mesh *me)
+static void edgetag_ensure_cd_flag(Mesh *me, const char edge_mode)
{
BMesh *bm = me->edit_btmesh->bm;
- switch (scene->toolsettings->edge_mode) {
+ switch (edge_mode) {
case EDGE_MODE_TAG_CREASE:
BM_mesh_cd_flag_ensure(bm, me, ME_CDFLAG_EDGE_CREASE);
break;
@@ -314,10 +318,9 @@ static void edgetag_ensure_cd_flag(Scene *scene, Mesh *me)
/* since you want to create paths with multiple selects, it doesn't have extend option */
static void mouse_mesh_shortest_path_edge(
- Scene *scene, const struct PathSelectParams *op_params,
+ Scene *scene, Object *obedit, const struct PathSelectParams *op_params,
BMEdge *e_act, BMEdge *e_dst)
{
- Object *obedit = scene->obedit;
BMEditMesh *em = BKE_editmesh_from_object(obedit);
BMesh *bm = em->bm;
@@ -326,7 +329,7 @@ static void mouse_mesh_shortest_path_edge(
Mesh *me = obedit->data;
bool is_path_ordered = false;
- edgetag_ensure_cd_flag(scene, obedit->data);
+ edgetag_ensure_cd_flag(obedit->data, op_params->edge_mode);
if (e_act && (e_act != e_dst)) {
if (op_params->use_fill) {
@@ -385,7 +388,7 @@ static void mouse_mesh_shortest_path_edge(
}
else {
const bool is_act = !edgetag_test_cb(e_dst, &user_data);
- edgetag_ensure_cd_flag(scene, obedit->data);
+ edgetag_ensure_cd_flag(obedit->data, op_params->edge_mode);
edgetag_set_cb(e_dst, is_act, &user_data); /* switch the edge option */
}
@@ -461,10 +464,9 @@ static void facetag_set_cb(BMFace *f, bool val, void *user_data_v)
}
static void mouse_mesh_shortest_path_face(
- Scene *scene, const struct PathSelectParams *op_params,
+ Scene *UNUSED(scene), Object *obedit, const struct PathSelectParams *op_params,
BMFace *f_act, BMFace *f_dst)
{
- Object *obedit = scene->obedit;
BMEditMesh *em = BKE_editmesh_from_object(obedit);
BMesh *bm = em->bm;
@@ -557,7 +559,7 @@ static void mouse_mesh_shortest_path_face(
* \{ */
static bool edbm_shortest_path_pick_ex(
- Scene *scene, const struct PathSelectParams *op_params,
+ Scene *scene, Object *obedit, const struct PathSelectParams *op_params,
BMElem *ele_src, BMElem *ele_dst)
{
@@ -565,15 +567,15 @@ static bool edbm_shortest_path_pick_ex(
/* pass */
}
else if (ele_src->head.htype == BM_VERT) {
- mouse_mesh_shortest_path_vert(scene, op_params, (BMVert *)ele_src, (BMVert *)ele_dst);
+ mouse_mesh_shortest_path_vert(scene, obedit, op_params, (BMVert *)ele_src, (BMVert *)ele_dst);
return true;
}
else if (ele_src->head.htype == BM_EDGE) {
- mouse_mesh_shortest_path_edge(scene, op_params, (BMEdge *)ele_src, (BMEdge *)ele_dst);
+ mouse_mesh_shortest_path_edge(scene, obedit, op_params, (BMEdge *)ele_src, (BMEdge *)ele_dst);
return true;
}
else if (ele_src->head.htype == BM_FACE) {
- mouse_mesh_shortest_path_face(scene, op_params, (BMFace *)ele_src, (BMFace *)ele_dst);
+ mouse_mesh_shortest_path_face(scene, obedit, op_params, (BMFace *)ele_src, (BMFace *)ele_dst);
return true;
}
@@ -652,7 +654,7 @@ static int edbm_shortest_path_pick_invoke(bContext *C, wmOperator *op, const wmE
op_params.track_active = track_active;
op_params.edge_mode = vc.scene->toolsettings->edge_mode;
- if (!edbm_shortest_path_pick_ex(vc.scene, &op_params, ele_src, ele_dst)) {
+ if (!edbm_shortest_path_pick_ex(vc.scene, vc.obedit, &op_params, ele_src, ele_dst)) {
return OPERATOR_PASS_THROUGH;
}
@@ -689,7 +691,7 @@ static int edbm_shortest_path_pick_exec(bContext *C, wmOperator *op)
op_params.track_active = true;
op_params.edge_mode = scene->toolsettings->edge_mode;
- if (!edbm_shortest_path_pick_ex(scene, &op_params, ele_src, ele_dst)) {
+ if (!edbm_shortest_path_pick_ex(scene, obedit, &op_params, ele_src, ele_dst)) {
return OPERATOR_CANCELLED;
}
@@ -730,67 +732,87 @@ void MESH_OT_shortest_path_pick(wmOperatorType *ot)
static int edbm_shortest_path_select_exec(bContext *C, wmOperator *op)
{
Scene *scene = CTX_data_scene(C);
- Object *ob = CTX_data_edit_object(C);
- BMEditMesh *em = BKE_editmesh_from_object(ob);
- BMesh *bm = em->bm;
- BMIter iter;
- BMEditSelection *ese_src, *ese_dst;
- BMElem *ele_src = NULL, *ele_dst = NULL, *ele;
+ bool found_valid_elements = false;
+
+ ViewLayer *view_layer = CTX_data_view_layer(C);
+ uint objects_len = 0;
+ Object **objects = BKE_view_layer_array_from_objects_in_edit_mode_unique_data(view_layer, &objects_len);
+ for (uint ob_index = 0; ob_index < objects_len; ob_index++) {
+ Object *obedit = objects[ob_index];
+ BMEditMesh *em = BKE_editmesh_from_object(obedit);
+ BMesh *bm = em->bm;
+ BMIter iter;
+ BMEditSelection *ese_src, *ese_dst;
+ BMElem *ele_src = NULL, *ele_dst = NULL, *ele;
+
+ if ((em->bm->totvertsel == 0) &&
+ (em->bm->totedgesel == 0) &&
+ (em->bm->totfacesel == 0))
+ {
+ continue;
+ }
- /* first try to find vertices in edit selection */
- ese_src = bm->selected.last;
- if (ese_src && (ese_dst = ese_src->prev) && (ese_src->htype == ese_dst->htype)) {
- ele_src = ese_src->ele;
- ele_dst = ese_dst->ele;
- }
- else {
- /* if selection history isn't available, find two selected elements */
- ele_src = ele_dst = NULL;
- if ((em->selectmode & SCE_SELECT_VERTEX) && (bm->totvertsel >= 2)) {
- BM_ITER_MESH (ele, &iter, bm, BM_VERTS_OF_MESH) {
- if (BM_elem_flag_test(ele, BM_ELEM_SELECT)) {
- if (ele_src == NULL) ele_src = ele;
- else if (ele_dst == NULL) ele_dst = ele;
- else break;
+ /* first try to find vertices in edit selection */
+ ese_src = bm->selected.last;
+ if (ese_src && (ese_dst = ese_src->prev) && (ese_src->htype == ese_dst->htype)) {
+ ele_src = ese_src->ele;
+ ele_dst = ese_dst->ele;
+ }
+ else {
+ /* if selection history isn't available, find two selected elements */
+ ele_src = ele_dst = NULL;
+ if ((em->selectmode & SCE_SELECT_VERTEX) && (bm->totvertsel >= 2)) {
+ BM_ITER_MESH (ele, &iter, bm, BM_VERTS_OF_MESH) {
+ if (BM_elem_flag_test(ele, BM_ELEM_SELECT)) {
+ if (ele_src == NULL) ele_src = ele;
+ else if (ele_dst == NULL) ele_dst = ele;
+ else break;
+ }
}
}
- }
- if ((ele_dst == NULL) && (em->selectmode & SCE_SELECT_EDGE) && (bm->totedgesel >= 2)) {
- ele_src = NULL;
- BM_ITER_MESH (ele, &iter, bm, BM_EDGES_OF_MESH) {
- if (BM_elem_flag_test(ele, BM_ELEM_SELECT)) {
- if (ele_src == NULL) ele_src = ele;
- else if (ele_dst == NULL) ele_dst = ele;
- else break;
+ if ((ele_dst == NULL) && (em->selectmode & SCE_SELECT_EDGE) && (bm->totedgesel >= 2)) {
+ ele_src = NULL;
+ BM_ITER_MESH (ele, &iter, bm, BM_EDGES_OF_MESH) {
+ if (BM_elem_flag_test(ele, BM_ELEM_SELECT)) {
+ if (ele_src == NULL) ele_src = ele;
+ else if (ele_dst == NULL) ele_dst = ele;
+ else break;
+ }
}
}
- }
- if ((ele_dst == NULL) && (em->selectmode & SCE_SELECT_FACE) && (bm->totfacesel >= 2)) {
- ele_src = NULL;
- BM_ITER_MESH (ele, &iter, bm, BM_FACES_OF_MESH) {
- if (BM_elem_flag_test(ele, BM_ELEM_SELECT)) {
- if (ele_src == NULL) ele_src = ele;
- else if (ele_dst == NULL) ele_dst = ele;
- else break;
+ if ((ele_dst == NULL) && (em->selectmode & SCE_SELECT_FACE) && (bm->totfacesel >= 2)) {
+ ele_src = NULL;
+ BM_ITER_MESH (ele, &iter, bm, BM_FACES_OF_MESH) {
+ if (BM_elem_flag_test(ele, BM_ELEM_SELECT)) {
+ if (ele_src == NULL) ele_src = ele;
+ else if (ele_dst == NULL) ele_dst = ele;
+ else break;
+ }
}
}
}
- }
- if (ele_src && ele_dst) {
- struct PathSelectParams op_params;
- path_select_params_from_op(op, &op_params);
+ if (ele_src && ele_dst) {
+ struct PathSelectParams op_params;
+ path_select_params_from_op(op, &op_params);
- edbm_shortest_path_pick_ex(scene, &op_params, ele_src, ele_dst);
+ edbm_shortest_path_pick_ex(scene, obedit, &op_params, ele_src, ele_dst);
- return OPERATOR_FINISHED;
+ found_valid_elements = true;
+ }
}
- else {
- BKE_report(op->reports, RPT_WARNING, "Path selection requires two matching elements to be selected");
+ MEM_freeN(objects);
+
+ if (!found_valid_elements) {
+ BKE_report(op->reports,
+ RPT_WARNING,
+ "Path selection requires two matching elements to be selected");
return OPERATOR_CANCELLED;
}
+
+ return OPERATOR_FINISHED;
}
void MESH_OT_shortest_path_select(wmOperatorType *ot)