Cleanup: style
[blender.git] / source / blender / editors / mesh / editmesh_tools.c
1 /*
2  * ***** BEGIN GPL LICENSE BLOCK *****
3  *
4  * This program is free software; you can redistribute it and/or
5  * modify it under the terms of the GNU General Public License
6  * as published by the Free Software Foundation; either version 2
7  * of the License, or (at your option) any later version.
8  *
9  * This program is distributed in the hope that it will be useful,
10  * but WITHOUT ANY WARRANTY; without even the implied warranty of
11  * MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE.  See the
12  * GNU General Public License for more details.
13  *
14  * You should have received a copy of the GNU General Public License
15  * along with this program; if not, write to the Free Software Foundation,
16  * Inc., 51 Franklin Street, Fifth Floor, Boston, MA 02110-1301, USA.
17  *
18  * The Original Code is Copyright (C) 2004 by Blender Foundation.
19  * All rights reserved.
20  *
21  * The Original Code is: all of this file.
22  *
23  * Contributor(s): Joseph Eagar
24  *
25  * ***** END GPL LICENSE BLOCK *****
26  */
27
28 /** \file blender/editors/mesh/editmesh_tools.c
29  *  \ingroup edmesh
30  */
31
32 #include <stddef.h>
33
34 #include "MEM_guardedalloc.h"
35
36 #include "DNA_key_types.h"
37 #include "DNA_material_types.h"
38 #include "DNA_mesh_types.h"
39 #include "DNA_meshdata_types.h"
40 #include "DNA_modifier_types.h"
41 #include "DNA_object_types.h"
42 #include "DNA_scene_types.h"
43
44 #include "BLI_bitmap.h"
45 #include "BLI_heap.h"
46 #include "BLI_listbase.h"
47 #include "BLI_linklist.h"
48 #include "BLI_linklist_stack.h"
49 #include "BLI_noise.h"
50 #include "BLI_math.h"
51 #include "BLI_rand.h"
52 #include "BLI_sort_utils.h"
53 #include "BLI_string.h"
54
55 #include "BKE_layer.h"
56 #include "BKE_material.h"
57 #include "BKE_context.h"
58 #include "BKE_deform.h"
59 #include "BKE_report.h"
60 #include "BKE_texture.h"
61 #include "BKE_main.h"
62 #include "BKE_mesh.h"
63 #include "BKE_editmesh.h"
64 #include "BKE_key.h"
65
66 #include "DEG_depsgraph.h"
67 #include "DEG_depsgraph_build.h"
68
69 #include "BLT_translation.h"
70
71 #include "RNA_define.h"
72 #include "RNA_access.h"
73 #include "RNA_enum_types.h"
74
75 #include "WM_api.h"
76 #include "WM_types.h"
77
78 #include "ED_mesh.h"
79 #include "ED_object.h"
80 #include "ED_screen.h"
81 #include "ED_transform.h"
82 #include "ED_transform_snap_object_context.h"
83 #include "ED_uvedit.h"
84 #include "ED_view3d.h"
85
86 #include "RE_render_ext.h"
87
88 #include "UI_interface.h"
89 #include "UI_resources.h"
90
91 #include "mesh_intern.h"  /* own include */
92
93 #include "bmesh_tools.h"
94
95 #define USE_FACE_CREATE_SEL_EXTEND
96
97 /* -------------------------------------------------------------------- */
98 /** \name Subdivide Operator
99  * \{ */
100
101 static int edbm_subdivide_exec(bContext *C, wmOperator *op)
102 {
103         const int cuts = RNA_int_get(op->ptr, "number_cuts");
104         const float smooth = RNA_float_get(op->ptr, "smoothness");
105         const float fractal = RNA_float_get(op->ptr, "fractal") / 2.5f;
106         const float along_normal = RNA_float_get(op->ptr, "fractal_along_normal");
107
108         if (RNA_boolean_get(op->ptr, "ngon") &&
109             RNA_enum_get(op->ptr, "quadcorner") == SUBD_CORNER_STRAIGHT_CUT)
110         {
111                 RNA_enum_set(op->ptr, "quadcorner", SUBD_CORNER_INNERVERT);
112         }
113         const int quad_corner_type = RNA_enum_get(op->ptr, "quadcorner");
114         const bool use_quad_tri = !RNA_boolean_get(op->ptr, "ngon");
115         const int seed = RNA_int_get(op->ptr, "seed");
116
117         ViewLayer *view_layer = CTX_data_view_layer(C);
118         uint objects_len = 0;
119         Object **objects = BKE_view_layer_array_from_objects_in_edit_mode_unique_data(view_layer, &objects_len);
120
121         for (uint ob_index = 0; ob_index < objects_len; ob_index++) {
122                 Object *obedit = objects[ob_index];
123                 BMEditMesh *em = BKE_editmesh_from_object(obedit);
124
125                 if (!(em->bm->totedgesel || em->bm->totfacesel)) {
126                         continue;
127                 }
128
129                 BM_mesh_esubdivide(
130                         em->bm, BM_ELEM_SELECT,
131                         smooth, SUBD_FALLOFF_LIN, false,
132                         fractal, along_normal,
133                         cuts,
134                         SUBDIV_SELECT_ORIG, quad_corner_type,
135                         use_quad_tri, true, false,
136                         seed);
137
138                 EDBM_update_generic(em, true, true);
139         }
140
141         MEM_freeN(objects);
142
143         return OPERATOR_FINISHED;
144 }
145
146 /* Note, these values must match delete_mesh() event values */
147 static const EnumPropertyItem prop_mesh_cornervert_types[] = {
148         {SUBD_CORNER_INNERVERT,     "INNERVERT", 0,      "Inner Vert", ""},
149         {SUBD_CORNER_PATH,          "PATH", 0,           "Path", ""},
150         {SUBD_CORNER_STRAIGHT_CUT,  "STRAIGHT_CUT", 0,   "Straight Cut", ""},
151         {SUBD_CORNER_FAN,           "FAN", 0,            "Fan", ""},
152         {0, NULL, 0, NULL, NULL}
153 };
154
155 void MESH_OT_subdivide(wmOperatorType *ot)
156 {
157         PropertyRNA *prop;
158
159         /* identifiers */
160         ot->name = "Subdivide";
161         ot->description = "Subdivide selected edges";
162         ot->idname = "MESH_OT_subdivide";
163
164         /* api callbacks */
165         ot->exec = edbm_subdivide_exec;
166         ot->poll = ED_operator_editmesh;
167
168         /* flags */
169         ot->flag = OPTYPE_REGISTER | OPTYPE_UNDO;
170
171         /* properties */
172         prop = RNA_def_int(ot->srna, "number_cuts", 1, 1, 100, "Number of Cuts", "", 1, 10);
173         /* avoid re-using last var because it can cause _very_ high poly meshes and annoy users (or worse crash) */
174         RNA_def_property_flag(prop, PROP_SKIP_SAVE);
175
176         RNA_def_float(ot->srna, "smoothness", 0.0f, 0.0f, 1e3f, "Smoothness", "Smoothness factor", 0.0f, 1.0f);
177
178         WM_operatortype_props_advanced_begin(ot);
179
180         RNA_def_boolean(ot->srna, "ngon", true, "Create N-Gons", "When disabled, newly created faces are limited to 3-4 sided faces");
181         RNA_def_enum(ot->srna, "quadcorner", prop_mesh_cornervert_types, SUBD_CORNER_STRAIGHT_CUT,
182                      "Quad Corner Type", "How to subdivide quad corners (anything other than Straight Cut will prevent ngons)");
183
184         RNA_def_float(ot->srna, "fractal", 0.0f, 0.0f, 1e6f, "Fractal", "Fractal randomness factor", 0.0f, 1000.0f);
185         RNA_def_float(ot->srna, "fractal_along_normal", 0.0f, 0.0f, 1.0f,
186                       "Along Normal", "Apply fractal displacement along normal only", 0.0f, 1.0f);
187         RNA_def_int(ot->srna, "seed", 0, 0, INT_MAX, "Random Seed", "Seed for the random number generator", 0, 255);
188 }
189
190 /** \} */
191
192 /* -------------------------------------------------------------------- */
193 /** \name Edge Ring Subdivide Operator
194  *
195  * Bridge code shares props.
196  *
197  * \{ */
198
199 struct EdgeRingOpSubdProps {
200         int interp_mode;
201         int cuts;
202         float smooth;
203
204         int profile_shape;
205         float profile_shape_factor;
206 };
207
208
209 static void mesh_operator_edgering_props(wmOperatorType *ot, const int cuts_min, const int cuts_default)
210 {
211         /* Note, these values must match delete_mesh() event values */
212         static const EnumPropertyItem prop_subd_edgering_types[] = {
213                 {SUBD_RING_INTERP_LINEAR, "LINEAR", 0, "Linear", ""},
214                 {SUBD_RING_INTERP_PATH, "PATH", 0, "Blend Path", ""},
215                 {SUBD_RING_INTERP_SURF, "SURFACE", 0, "Blend Surface", ""},
216                 {0, NULL, 0, NULL, NULL}
217         };
218
219         PropertyRNA *prop;
220
221         prop = RNA_def_int(ot->srna, "number_cuts", cuts_default, 0, 1000, "Number of Cuts", "", cuts_min, 64);
222         RNA_def_property_flag(prop, PROP_SKIP_SAVE);
223
224         RNA_def_enum(ot->srna, "interpolation", prop_subd_edgering_types, SUBD_RING_INTERP_PATH,
225                      "Interpolation", "Interpolation method");
226
227         RNA_def_float(ot->srna, "smoothness", 1.0f, 0.0f, 1e3f,
228                       "Smoothness", "Smoothness factor", 0.0f, 2.0f);
229
230         /* profile-shape */
231         RNA_def_float(ot->srna, "profile_shape_factor", 0.0f, -1e3f, 1e3f,
232                       "Profile Factor", "How much intermediary new edges are shrunk/expanded", -2.0f, 2.0f);
233
234         prop = RNA_def_property(ot->srna, "profile_shape", PROP_ENUM, PROP_NONE);
235         RNA_def_property_enum_items(prop, rna_enum_proportional_falloff_curve_only_items);
236         RNA_def_property_enum_default(prop, PROP_SMOOTH);
237         RNA_def_property_ui_text(prop, "Profile Shape", "Shape of the profile");
238         RNA_def_property_translation_context(prop, BLT_I18NCONTEXT_ID_CURVE); /* Abusing id_curve :/ */
239 }
240
241 static void mesh_operator_edgering_props_get(wmOperator *op, struct EdgeRingOpSubdProps *op_props)
242 {
243         op_props->interp_mode = RNA_enum_get(op->ptr, "interpolation");
244         op_props->cuts = RNA_int_get(op->ptr, "number_cuts");
245         op_props->smooth = RNA_float_get(op->ptr, "smoothness");
246
247         op_props->profile_shape = RNA_enum_get(op->ptr, "profile_shape");
248         op_props->profile_shape_factor = RNA_float_get(op->ptr, "profile_shape_factor");
249 }
250
251 static int edbm_subdivide_edge_ring_exec(bContext *C, wmOperator *op)
252 {
253
254         ViewLayer *view_layer = CTX_data_view_layer(C);
255         uint objects_len = 0;
256         Object * *objects = BKE_view_layer_array_from_objects_in_edit_mode_unique_data(view_layer, &objects_len);
257         struct EdgeRingOpSubdProps op_props;
258
259         mesh_operator_edgering_props_get(op, &op_props);
260
261         for (uint ob_index = 0; ob_index < objects_len; ob_index++) {
262                 Object * obedit = objects[ob_index];
263                 BMEditMesh * em = BKE_editmesh_from_object(obedit);
264
265                 if (em->bm->totedgesel == 0) {
266                         continue;
267                 }
268
269                 if (!EDBM_op_callf(
270                         em, op,
271                         "subdivide_edgering edges=%he interp_mode=%i cuts=%i smooth=%f "
272                         "profile_shape=%i profile_shape_factor=%f",
273                         BM_ELEM_SELECT, op_props.interp_mode, op_props.cuts, op_props.smooth,
274                         op_props.profile_shape, op_props.profile_shape_factor))
275                 {
276                         continue;
277                 }
278
279                 EDBM_update_generic(em, true, true);
280         }
281
282         MEM_freeN(objects);
283         return OPERATOR_FINISHED;
284 }
285
286 void MESH_OT_subdivide_edgering(wmOperatorType *ot)
287 {
288         /* identifiers */
289         ot->name = "Subdivide Edge-Ring";
290         ot->description = "";
291         ot->idname = "MESH_OT_subdivide_edgering";
292
293         /* api callbacks */
294         ot->exec = edbm_subdivide_edge_ring_exec;
295         ot->poll = ED_operator_editmesh;
296
297         /* flags */
298         ot->flag = OPTYPE_REGISTER | OPTYPE_UNDO;
299
300         /* properties */
301         mesh_operator_edgering_props(ot, 1, 10);
302 }
303
304 /** \} */
305
306 /* -------------------------------------------------------------------- */
307 /** \name Un-Subdivide Operator
308  * \{ */
309
310 static int edbm_unsubdivide_exec(bContext *C, wmOperator *op)
311 {
312         const int iterations = RNA_int_get(op->ptr, "iterations");
313         ViewLayer *view_layer = CTX_data_view_layer(C);
314         uint objects_len = 0;
315         Object **objects = BKE_view_layer_array_from_objects_in_edit_mode(view_layer, &objects_len);
316         for (uint ob_index = 0; ob_index < objects_len; ob_index++) {
317                 Object *obedit = objects[ob_index];
318                 BMEditMesh *em = BKE_editmesh_from_object(obedit);
319
320                 if ((em->bm->totvertsel == 0) &&
321                     (em->bm->totedgesel == 0) &&
322                     (em->bm->totfacesel == 0))
323                 {
324                         continue;
325                 }
326
327                 BMOperator bmop;
328                 EDBM_op_init(em, &bmop, op,
329                        "unsubdivide verts=%hv iterations=%i", BM_ELEM_SELECT, iterations);
330
331                 BMO_op_exec(em->bm, &bmop);
332
333                 if (!EDBM_op_finish(em, &bmop, op, true)) {
334                         continue;
335                 }
336
337                 if ((em->selectmode & SCE_SELECT_VERTEX) == 0) {
338                         EDBM_selectmode_flush_ex(em, SCE_SELECT_VERTEX);  /* need to flush vert->face first */
339                 }
340                 EDBM_selectmode_flush(em);
341
342                 EDBM_update_generic(em, true, true);
343         }
344         MEM_freeN(objects);
345
346         return OPERATOR_FINISHED;
347 }
348
349 void MESH_OT_unsubdivide(wmOperatorType *ot)
350 {
351         /* identifiers */
352         ot->name = "Un-Subdivide";
353         ot->description = "UnSubdivide selected edges & faces";
354         ot->idname = "MESH_OT_unsubdivide";
355
356         /* api callbacks */
357         ot->exec = edbm_unsubdivide_exec;
358         ot->poll = ED_operator_editmesh;
359
360         /* flags */
361         ot->flag = OPTYPE_REGISTER | OPTYPE_UNDO;
362
363         /* props */
364         RNA_def_int(ot->srna, "iterations", 2, 1, 1000, "Iterations", "Number of times to unsubdivide", 1, 100);
365 }
366
367 void EDBM_project_snap_verts(bContext *C, ARegion *ar, BMEditMesh *em)
368 {
369         Main *bmain = CTX_data_main(C);
370         Object *obedit = em->ob;
371         BMIter iter;
372         BMVert *eve;
373
374         ED_view3d_init_mats_rv3d(obedit, ar->regiondata);
375
376         struct SnapObjectContext *snap_context = ED_transform_snap_object_context_create_view3d(
377                 bmain, CTX_data_scene(C), CTX_data_depsgraph(C), 0,
378                 ar, CTX_wm_view3d(C));
379
380         BM_ITER_MESH (eve, &iter, em->bm, BM_VERTS_OF_MESH) {
381                 if (BM_elem_flag_test(eve, BM_ELEM_SELECT)) {
382                         float mval[2], co_proj[3];
383                         if (ED_view3d_project_float_object(ar, eve->co, mval, V3D_PROJ_TEST_NOP) == V3D_PROJ_RET_OK) {
384                                 if (ED_transform_snap_object_project_view3d(
385                                         snap_context,
386                                         SCE_SNAP_MODE_FACE,
387                                         &(const struct SnapObjectParams){
388                                             .snap_select = SNAP_NOT_ACTIVE,
389                                             .use_object_edit_cage = false,
390                                             .use_occlusion_test = true,
391                                         },
392                                         mval, NULL,
393                                         co_proj, NULL))
394                                 {
395                                         mul_v3_m4v3(eve->co, obedit->imat, co_proj);
396                                 }
397                         }
398                 }
399         }
400
401         ED_transform_snap_object_context_destroy(snap_context);
402 }
403
404 /** \} */
405
406 /* -------------------------------------------------------------------- */
407 /** \name Delete Operator
408  * \{ */
409
410 /* Note, these values must match delete_mesh() event values */
411 enum {
412         MESH_DELETE_VERT      = 0,
413         MESH_DELETE_EDGE      = 1,
414         MESH_DELETE_FACE      = 2,
415         MESH_DELETE_EDGE_FACE = 3,
416         MESH_DELETE_ONLY_FACE = 4,
417 };
418
419 static void edbm_report_delete_info(ReportList *reports, const int totelem_old[3], const int totelem_new[3])
420 {
421         BKE_reportf(reports, RPT_INFO,
422                     "Removed: %d vertices, %d edges, %d faces",
423                     totelem_old[0] - totelem_new[0], totelem_old[1] - totelem_new[1], totelem_old[2] - totelem_new[2]);
424 }
425
426 static int edbm_delete_exec(bContext *C, wmOperator *op)
427 {
428         ViewLayer *view_layer = CTX_data_view_layer(C);
429
430         uint objects_len = 0;
431         Object **objects = BKE_view_layer_array_from_objects_in_edit_mode_unique_data(view_layer, &objects_len);
432         bool changed_multi = false;
433
434         for (uint ob_index = 0; ob_index < objects_len; ob_index++) {
435                 Object *obedit = objects[ob_index];
436                 BMEditMesh *em = BKE_editmesh_from_object(obedit);
437                 const int type = RNA_enum_get(op->ptr, "type");
438
439                 switch (type) {
440                         case MESH_DELETE_VERT: /* Erase Vertices */
441                                 if (!(em->bm->totvertsel &&
442                                       EDBM_op_callf(em, op, "delete geom=%hv context=%i", BM_ELEM_SELECT, DEL_VERTS)))
443                                 {
444                                         continue;
445                                 }
446                                 break;
447                         case MESH_DELETE_EDGE: /* Erase Edges */
448                                 if (!(em->bm->totedgesel &&
449                                       EDBM_op_callf(em, op, "delete geom=%he context=%i", BM_ELEM_SELECT, DEL_EDGES)))
450                                 {
451                                         continue;
452                                 }
453                                 break;
454                         case MESH_DELETE_FACE: /* Erase Faces */
455                                 if (!(em->bm->totfacesel &&
456                                       EDBM_op_callf(em, op, "delete geom=%hf context=%i", BM_ELEM_SELECT, DEL_FACES)))
457                                 {
458                                         continue;
459                                 }
460                                 break;
461                         case MESH_DELETE_EDGE_FACE:
462                                 /* Edges and Faces */
463                                 if (!((em->bm->totedgesel || em->bm->totfacesel) &&
464                                       EDBM_op_callf(em, op, "delete geom=%hef context=%i", BM_ELEM_SELECT, DEL_EDGESFACES)))
465                                 {
466                                         continue;
467                                 }
468                                 break;
469                         case MESH_DELETE_ONLY_FACE:
470                                 /* Only faces. */
471                                 if (!(em->bm->totfacesel &&
472                                       EDBM_op_callf(em, op, "delete geom=%hf context=%i", BM_ELEM_SELECT, DEL_ONLYFACES)))
473                                 {
474                                         continue;
475                                 }
476                                 break;
477                         default:
478                                 BLI_assert(0);
479                                 break;
480                 }
481
482                 changed_multi = true;
483
484                 EDBM_flag_disable_all(em, BM_ELEM_SELECT);
485
486                 EDBM_update_generic(em, true, true);
487         }
488
489         MEM_freeN(objects);
490
491         return changed_multi ? OPERATOR_FINISHED : OPERATOR_CANCELLED;
492 }
493
494 void MESH_OT_delete(wmOperatorType *ot)
495 {
496         static const EnumPropertyItem prop_mesh_delete_types[] = {
497                 {MESH_DELETE_VERT,      "VERT",      0, "Vertices", ""},
498                 {MESH_DELETE_EDGE,      "EDGE",      0, "Edges", ""},
499                 {MESH_DELETE_FACE,      "FACE",      0, "Faces", ""},
500                 {MESH_DELETE_EDGE_FACE, "EDGE_FACE", 0, "Only Edges & Faces", ""},
501                 {MESH_DELETE_ONLY_FACE, "ONLY_FACE", 0, "Only Faces", ""},
502                 {0, NULL, 0, NULL, NULL}
503         };
504
505         /* identifiers */
506         ot->name = "Delete";
507         ot->description = "Delete selected vertices, edges or faces";
508         ot->idname = "MESH_OT_delete";
509
510         /* api callbacks */
511         ot->invoke = WM_menu_invoke;
512         ot->exec = edbm_delete_exec;
513
514         ot->poll = ED_operator_editmesh;
515
516         /* flags */
517         ot->flag = OPTYPE_REGISTER | OPTYPE_UNDO;
518
519         /* props */
520         ot->prop = RNA_def_enum(ot->srna, "type", prop_mesh_delete_types, MESH_DELETE_VERT,
521                                 "Type", "Method used for deleting mesh data");
522         RNA_def_property_flag(ot->prop, PROP_HIDDEN | PROP_SKIP_SAVE);
523 }
524
525 /** \} */
526
527 /* -------------------------------------------------------------------- */
528 /** \name Delete Loose Operator
529  * \{ */
530
531 static bool bm_face_is_loose(BMFace *f)
532 {
533         BMLoop *l_iter, *l_first;
534
535         l_iter = l_first = BM_FACE_FIRST_LOOP(f);
536         do {
537                 if (!BM_edge_is_boundary(l_iter->e)) {
538                         return false;
539                 }
540         } while ((l_iter = l_iter->next) != l_first);
541
542         return true;
543 }
544
545 static int edbm_delete_loose_exec(bContext *C, wmOperator *op)
546 {
547         ViewLayer *view_layer = CTX_data_view_layer(C);
548         int totelem_old_sel[3];
549         int totelem_old[3];
550
551         uint objects_len = 0;
552         Object **objects = BKE_view_layer_array_from_objects_in_edit_mode_unique_data(view_layer, &objects_len);
553
554         EDBM_mesh_stats_multi(objects, objects_len, totelem_old, totelem_old_sel);
555
556         const bool use_verts = (RNA_boolean_get(op->ptr, "use_verts") && totelem_old_sel[0]);
557         const bool use_edges = (RNA_boolean_get(op->ptr, "use_edges") && totelem_old_sel[1]);
558         const bool use_faces = (RNA_boolean_get(op->ptr, "use_faces") && totelem_old_sel[2]);
559
560         for (uint ob_index = 0; ob_index < objects_len; ob_index++) {
561                 Object *obedit = objects[ob_index];
562
563                 BMEditMesh *em = BKE_editmesh_from_object(obedit);
564                 BMesh *bm = em->bm;
565                 BMIter iter;
566
567                 BM_mesh_elem_hflag_disable_all(bm, BM_VERT | BM_EDGE | BM_FACE, BM_ELEM_TAG, false);
568
569                 if (use_faces) {
570                         BMFace *f;
571
572                         BM_ITER_MESH (f, &iter, bm, BM_FACES_OF_MESH) {
573                                 if (BM_elem_flag_test(f, BM_ELEM_SELECT)) {
574                                         BM_elem_flag_set(f, BM_ELEM_TAG, bm_face_is_loose(f));
575                                 }
576                         }
577
578                         BM_mesh_delete_hflag_context(bm, BM_ELEM_TAG, DEL_FACES);
579                 }
580
581                 if (use_edges) {
582                         BMEdge *e;
583
584                         BM_ITER_MESH (e, &iter, bm, BM_EDGES_OF_MESH) {
585                                 if (BM_elem_flag_test(e, BM_ELEM_SELECT)) {
586                                         BM_elem_flag_set(e, BM_ELEM_TAG, BM_edge_is_wire(e));
587                                 }
588                         }
589
590                         BM_mesh_delete_hflag_context(bm, BM_ELEM_TAG, DEL_EDGES);
591                 }
592
593                 if (use_verts) {
594                         BMVert *v;
595
596                         BM_ITER_MESH (v, &iter, bm, BM_VERTS_OF_MESH) {
597                                 if (BM_elem_flag_test(v, BM_ELEM_SELECT)) {
598                                         BM_elem_flag_set(v, BM_ELEM_TAG, (v->e == NULL));
599                                 }
600                         }
601
602                         BM_mesh_delete_hflag_context(bm, BM_ELEM_TAG, DEL_VERTS);
603                 }
604
605                 EDBM_flag_disable_all(em, BM_ELEM_SELECT);
606
607                 EDBM_update_generic(em, true, true);
608         }
609
610         int totelem_new[3];
611         EDBM_mesh_stats_multi(objects, objects_len, totelem_new, NULL);
612
613         edbm_report_delete_info(op->reports, totelem_old, totelem_new);
614
615         MEM_freeN(objects);
616
617         return OPERATOR_FINISHED;
618 }
619
620
621 void MESH_OT_delete_loose(wmOperatorType *ot)
622 {
623         /* identifiers */
624         ot->name = "Delete Loose";
625         ot->description = "Delete loose vertices, edges or faces";
626         ot->idname = "MESH_OT_delete_loose";
627
628         /* api callbacks */
629         ot->exec = edbm_delete_loose_exec;
630
631         ot->poll = ED_operator_editmesh;
632
633         /* flags */
634         ot->flag = OPTYPE_REGISTER | OPTYPE_UNDO;
635
636         /* props */
637         RNA_def_boolean(ot->srna, "use_verts", true, "Vertices", "Remove loose vertices");
638         RNA_def_boolean(ot->srna, "use_edges", true, "Edges", "Remove loose edges");
639         RNA_def_boolean(ot->srna, "use_faces", false, "Faces", "Remove loose faces");
640 }
641
642 /** \} */
643
644 /* -------------------------------------------------------------------- */
645 /** \name Collapse Edge Operator
646  * \{ */
647
648 static int edbm_collapse_edge_exec(bContext *C, wmOperator *op)
649 {
650         ViewLayer *view_layer = CTX_data_view_layer(C);
651         uint objects_len = 0;
652         Object **objects = BKE_view_layer_array_from_objects_in_edit_mode_unique_data(view_layer, &objects_len);
653         for (uint ob_index = 0; ob_index < objects_len; ob_index++) {
654                 Object *obedit = objects[ob_index];
655                 BMEditMesh *em = BKE_editmesh_from_object(obedit);
656
657                 if (em->bm->totedgesel == 0) {
658                         continue;
659                 }
660
661                 if (!EDBM_op_callf(em, op, "collapse edges=%he uvs=%b", BM_ELEM_SELECT, true)) {
662                         continue;
663                 }
664
665                 EDBM_update_generic(em, true, true);
666         }
667         MEM_freeN(objects);
668
669         return OPERATOR_FINISHED;
670 }
671
672 void MESH_OT_edge_collapse(wmOperatorType *ot)
673 {
674         /* identifiers */
675         ot->name = "Edge Collapse";
676         ot->description = "Collapse selected edges";
677         ot->idname = "MESH_OT_edge_collapse";
678
679         /* api callbacks */
680         ot->exec = edbm_collapse_edge_exec;
681         ot->poll = ED_operator_editmesh;
682
683         /* flags */
684         ot->flag = OPTYPE_REGISTER | OPTYPE_UNDO;
685 }
686
687 /** \} */
688
689 /* -------------------------------------------------------------------- */
690 /** \name Create Edge/Face Operator
691  * \{ */
692
693 static bool edbm_add_edge_face__smooth_get(BMesh *bm)
694 {
695         BMEdge *e;
696         BMIter iter;
697
698         unsigned int vote_on_smooth[2] = {0, 0};
699
700         BM_ITER_MESH (e, &iter, bm, BM_EDGES_OF_MESH) {
701                 if (BM_elem_flag_test(e, BM_ELEM_SELECT) && e->l) {
702                         vote_on_smooth[BM_elem_flag_test_bool(e->l->f, BM_ELEM_SMOOTH)]++;
703                 }
704         }
705
706         return (vote_on_smooth[0] < vote_on_smooth[1]);
707 }
708
709 #ifdef USE_FACE_CREATE_SEL_EXTEND
710 /**
711  * Function used to get a fixed number of edges linked to a vertex that passes a test function.
712  * This is used so we can request all boundary edges connected to a vertex for eg.
713  */
714 static int edbm_add_edge_face_exec__vert_edge_lookup(
715         BMVert *v, BMEdge *e_used, BMEdge **e_arr, const int e_arr_len,
716         bool (* func)(const BMEdge *))
717 {
718         BMIter iter;
719         BMEdge *e_iter;
720         int i = 0;
721         BM_ITER_ELEM (e_iter, &iter, v, BM_EDGES_OF_VERT) {
722                 if (BM_elem_flag_test(e_iter, BM_ELEM_HIDDEN) == false) {
723                         if ((e_used == NULL) || (e_used != e_iter)) {
724                                 if (func(e_iter)) {
725                                         e_arr[i++] = e_iter;
726                                         if (i >= e_arr_len) {
727                                                 break;
728                                         }
729                                 }
730                         }
731                 }
732         }
733         return i;
734 }
735
736 static BMElem *edbm_add_edge_face_exec__tricky_extend_sel(BMesh *bm)
737 {
738         BMIter iter;
739         bool found = false;
740
741         if (bm->totvertsel == 1 && bm->totedgesel == 0 && bm->totfacesel == 0) {
742                 /* first look for 2 boundary edges */
743                 BMVert *v;
744
745                 BM_ITER_MESH (v, &iter, bm, BM_VERTS_OF_MESH) {
746                         if (BM_elem_flag_test(v, BM_ELEM_SELECT)) {
747                                 found = true;
748                                 break;
749                         }
750                 }
751
752                 if (found) {
753                         BMEdge *ed_pair[3];
754                         if (
755                             ((edbm_add_edge_face_exec__vert_edge_lookup(v, NULL, ed_pair, 3, BM_edge_is_wire) == 2) &&
756                              (BM_edge_share_face_check(ed_pair[0], ed_pair[1]) == false)) ||
757
758                             ((edbm_add_edge_face_exec__vert_edge_lookup(v, NULL, ed_pair, 3, BM_edge_is_boundary) == 2) &&
759                              (BM_edge_share_face_check(ed_pair[0], ed_pair[1]) == false))
760                             )
761                         {
762                                 BMEdge *e_other = BM_edge_exists(
763                                         BM_edge_other_vert(ed_pair[0], v),
764                                         BM_edge_other_vert(ed_pair[1], v));
765                                 BM_edge_select_set(bm, ed_pair[0], true);
766                                 BM_edge_select_set(bm, ed_pair[1], true);
767                                 if (e_other) {
768                                         BM_edge_select_set(bm, e_other, true);
769                                 }
770                                 return (BMElem *)v;
771                         }
772                 }
773         }
774         else if (bm->totvertsel == 2 && bm->totedgesel == 1 && bm->totfacesel == 0) {
775                 /* first look for 2 boundary edges */
776                 BMEdge *e;
777
778                 BM_ITER_MESH (e, &iter, bm, BM_EDGES_OF_MESH) {
779                         if (BM_elem_flag_test(e, BM_ELEM_SELECT)) {
780                                 found = true;
781                                 break;
782                         }
783                 }
784                 if (found) {
785                         BMEdge *ed_pair_v1[2];
786                         BMEdge *ed_pair_v2[2];
787                         if (
788                             ((edbm_add_edge_face_exec__vert_edge_lookup(e->v1, e, ed_pair_v1, 2, BM_edge_is_wire) == 1) &&
789                              (edbm_add_edge_face_exec__vert_edge_lookup(e->v2, e, ed_pair_v2, 2, BM_edge_is_wire) == 1) &&
790                              (BM_edge_share_face_check(e, ed_pair_v1[0]) == false) &&
791                              (BM_edge_share_face_check(e, ed_pair_v2[0]) == false)) ||
792
793 #if 1  /* better support mixed cases [#37203] */
794                             ((edbm_add_edge_face_exec__vert_edge_lookup(e->v1, e, ed_pair_v1, 2, BM_edge_is_wire)     == 1) &&
795                              (edbm_add_edge_face_exec__vert_edge_lookup(e->v2, e, ed_pair_v2, 2, BM_edge_is_boundary) == 1) &&
796                              (BM_edge_share_face_check(e, ed_pair_v1[0]) == false) &&
797                              (BM_edge_share_face_check(e, ed_pair_v2[0]) == false)) ||
798
799                             ((edbm_add_edge_face_exec__vert_edge_lookup(e->v1, e, ed_pair_v1, 2, BM_edge_is_boundary) == 1) &&
800                              (edbm_add_edge_face_exec__vert_edge_lookup(e->v2, e, ed_pair_v2, 2, BM_edge_is_wire)     == 1) &&
801                              (BM_edge_share_face_check(e, ed_pair_v1[0]) == false) &&
802                              (BM_edge_share_face_check(e, ed_pair_v2[0]) == false)) ||
803 #endif
804
805                             ((edbm_add_edge_face_exec__vert_edge_lookup(e->v1, e, ed_pair_v1, 2, BM_edge_is_boundary) == 1) &&
806                              (edbm_add_edge_face_exec__vert_edge_lookup(e->v2, e, ed_pair_v2, 2, BM_edge_is_boundary) == 1) &&
807                              (BM_edge_share_face_check(e, ed_pair_v1[0]) == false) &&
808                              (BM_edge_share_face_check(e, ed_pair_v2[0]) == false))
809                             )
810                         {
811                                 BMVert *v1_other = BM_edge_other_vert(ed_pair_v1[0], e->v1);
812                                 BMVert *v2_other = BM_edge_other_vert(ed_pair_v2[0], e->v2);
813                                 BMEdge *e_other = (v1_other != v2_other) ? BM_edge_exists(v1_other, v2_other) : NULL;
814                                 BM_edge_select_set(bm, ed_pair_v1[0], true);
815                                 BM_edge_select_set(bm, ed_pair_v2[0], true);
816                                 if (e_other) {
817                                         BM_edge_select_set(bm, e_other, true);
818                                 }
819                                 return (BMElem *)e;
820                         }
821                 }
822         }
823
824         return NULL;
825 }
826 static void edbm_add_edge_face_exec__tricky_finalize_sel(BMesh *bm, BMElem *ele_desel, BMFace *f)
827 {
828         /* now we need to find the edge that isnt connected to this element */
829         BM_select_history_clear(bm);
830
831         /* Notes on hidden geometry:
832          * - un-hide the face since its possible hidden was copied when copying surrounding face attributes.
833          * - un-hide before adding to select history
834          *   since we may extend into an existing, hidden vert/edge.
835          */
836
837         BM_elem_flag_disable(f, BM_ELEM_HIDDEN);
838         BM_face_select_set(bm, f, false);
839
840         if (ele_desel->head.htype == BM_VERT) {
841                 BMLoop *l = BM_face_vert_share_loop(f, (BMVert *)ele_desel);
842                 BLI_assert(f->len == 3);
843                 BM_vert_select_set(bm, (BMVert *)ele_desel, false);
844                 BM_edge_select_set(bm, l->next->e, true);
845                 BM_select_history_store(bm, l->next->e);
846         }
847         else {
848                 BMLoop *l = BM_face_edge_share_loop(f, (BMEdge *)ele_desel);
849                 BLI_assert(f->len == 4 || f->len == 3);
850
851                 BM_edge_select_set(bm, (BMEdge *)ele_desel, false);
852                 if (f->len == 4) {
853                         BMEdge *e_active = l->next->next->e;
854                         BM_elem_flag_disable(e_active, BM_ELEM_HIDDEN);
855                         BM_edge_select_set(bm, e_active, true);
856                         BM_select_history_store(bm, e_active);
857                 }
858                 else {
859                         BMVert *v_active = l->next->next->v;
860                         BM_elem_flag_disable(v_active, BM_ELEM_HIDDEN);
861                         BM_vert_select_set(bm, v_active, true);
862                         BM_select_history_store(bm, v_active);
863                 }
864         }
865 }
866 #endif  /* USE_FACE_CREATE_SEL_EXTEND */
867
868 static int edbm_add_edge_face_exec(bContext *C, wmOperator *op)
869 {
870         /* when this is used to dissolve we could avoid this, but checking isnt too slow */
871
872         ViewLayer *view_layer = CTX_data_view_layer(C);
873         uint objects_len = 0;
874         Object **objects = BKE_view_layer_array_from_objects_in_edit_mode_unique_data(view_layer, &objects_len);
875         for (uint ob_index = 0; ob_index < objects_len; ob_index++) {
876                 Object *obedit = objects[ob_index];
877                 BMEditMesh *em = BKE_editmesh_from_object(obedit);
878
879                 if ((em->bm->totvertsel == 0) &&
880                     (em->bm->totedgesel == 0) &&
881                     (em->bm->totvertsel == 0))
882                 {
883                         continue;
884                 }
885
886                 bool use_smooth = edbm_add_edge_face__smooth_get(em->bm);
887                 int totedge_orig = em->bm->totedge;
888                 int totface_orig = em->bm->totface;
889
890                 BMOperator bmop;
891 #ifdef USE_FACE_CREATE_SEL_EXTEND
892                 BMElem *ele_desel;
893                 BMFace *ele_desel_face;
894
895                 /* be extra clever, figure out if a partial selection should be extended so we can create geometry
896                  * with single vert or single edge selection */
897                 ele_desel = edbm_add_edge_face_exec__tricky_extend_sel(em->bm);
898 #endif
899                 if (!EDBM_op_init(
900                             em, &bmop, op,
901                             "contextual_create geom=%hfev mat_nr=%i use_smooth=%b",
902                             BM_ELEM_SELECT, em->mat_nr, use_smooth))
903                 {
904                         continue;
905                 }
906
907                 BMO_op_exec(em->bm, &bmop);
908
909                 /* cancel if nothing was done */
910                 if ((totedge_orig == em->bm->totedge) &&
911                     (totface_orig == em->bm->totface))
912                 {
913                         EDBM_op_finish(em, &bmop, op, true);
914                         continue;
915                 }
916 #ifdef USE_FACE_CREATE_SEL_EXTEND
917                 /* normally we would want to leave the new geometry selected,
918                  * but being able to press F many times to add geometry is too useful! */
919                 if (ele_desel &&
920                     (BMO_slot_buffer_count(bmop.slots_out, "faces.out") == 1) &&
921                     (ele_desel_face = BMO_slot_buffer_get_first(bmop.slots_out, "faces.out")))
922                 {
923                         edbm_add_edge_face_exec__tricky_finalize_sel(em->bm, ele_desel, ele_desel_face);
924                 }
925                 else
926 #endif
927                 {
928                         /* Newly created faces may include existing hidden edges,
929                          * copying face data from surrounding, may have copied hidden face flag too.
930                          *
931                          * Important that faces use flushing since 'edges.out' wont include hidden edges that already existed.
932                          */
933                         BMO_slot_buffer_hflag_disable(em->bm, bmop.slots_out, "faces.out", BM_FACE, BM_ELEM_HIDDEN, true);
934                         BMO_slot_buffer_hflag_disable(em->bm, bmop.slots_out, "edges.out", BM_EDGE, BM_ELEM_HIDDEN, false);
935
936                         BMO_slot_buffer_hflag_enable(em->bm, bmop.slots_out, "faces.out", BM_FACE, BM_ELEM_SELECT, true);
937                         BMO_slot_buffer_hflag_enable(em->bm, bmop.slots_out, "edges.out", BM_EDGE, BM_ELEM_SELECT, true);
938                 }
939
940                 if (!EDBM_op_finish(em, &bmop, op, true)) {
941                         continue;
942                 }
943
944                 EDBM_update_generic(em, true, true);
945         }
946         MEM_freeN(objects);
947
948         return OPERATOR_FINISHED;
949 }
950
951 void MESH_OT_edge_face_add(wmOperatorType *ot)
952 {
953         /* identifiers */
954         ot->name = "Make Edge/Face";
955         ot->description = "Add an edge or face to selected";
956         ot->idname = "MESH_OT_edge_face_add";
957
958         /* api callbacks */
959         ot->exec = edbm_add_edge_face_exec;
960         ot->poll = ED_operator_editmesh;
961
962         /* flags */
963         ot->flag = OPTYPE_REGISTER | OPTYPE_UNDO;
964 }
965
966 /** \} */
967
968 /* -------------------------------------------------------------------- */
969 /** \name Mark Edge (Seam) Operator
970  * \{ */
971
972 static int edbm_mark_seam_exec(bContext *C, wmOperator *op)
973 {
974         Scene *scene = CTX_data_scene(C);
975         ViewLayer *view_layer = CTX_data_view_layer(C);
976         BMEdge *eed;
977         BMIter iter;
978         const bool clear = RNA_boolean_get(op->ptr, "clear");
979
980         uint objects_len = 0;
981         Object **objects = BKE_view_layer_array_from_objects_in_edit_mode_unique_data(view_layer, &objects_len);
982         for (uint ob_index = 0; ob_index < objects_len; ob_index++) {
983                 Object *obedit = objects[ob_index];
984                 BMEditMesh *em = BKE_editmesh_from_object(obedit);
985                 BMesh *bm = em->bm;
986
987                 if (bm->totedgesel == 0) {
988                         continue;
989                 }
990
991                 Mesh *me = ((Mesh *)obedit->data);
992
993                 /* auto-enable seams drawing */
994                 if (clear == 0) {
995                         me->drawflag |= ME_DRAWSEAMS;
996                 }
997
998                 if (clear) {
999                         BM_ITER_MESH (eed, &iter, bm, BM_EDGES_OF_MESH) {
1000                                 if (!BM_elem_flag_test(eed, BM_ELEM_SELECT) || BM_elem_flag_test(eed, BM_ELEM_HIDDEN)) {
1001                                         continue;
1002                                 }
1003
1004                                 BM_elem_flag_disable(eed, BM_ELEM_SEAM);
1005                         }
1006                 }
1007                 else {
1008                         BM_ITER_MESH (eed, &iter, bm, BM_EDGES_OF_MESH) {
1009                                 if (!BM_elem_flag_test(eed, BM_ELEM_SELECT) || BM_elem_flag_test(eed, BM_ELEM_HIDDEN)) {
1010                                         continue;
1011                                 }
1012                                 BM_elem_flag_enable(eed, BM_ELEM_SEAM);
1013                         }
1014                 }
1015
1016                 ED_uvedit_live_unwrap(scene, obedit);
1017                 EDBM_update_generic(em, true, false);
1018         }
1019         MEM_freeN(objects);
1020
1021         return OPERATOR_FINISHED;
1022 }
1023
1024 void MESH_OT_mark_seam(wmOperatorType *ot)
1025 {
1026         PropertyRNA *prop;
1027
1028         /* identifiers */
1029         ot->name = "Mark Seam";
1030         ot->idname = "MESH_OT_mark_seam";
1031         ot->description = "(Un)mark selected edges as a seam";
1032
1033         /* api callbacks */
1034         ot->exec = edbm_mark_seam_exec;
1035         ot->poll = ED_operator_editmesh;
1036
1037         /* flags */
1038         ot->flag = OPTYPE_REGISTER | OPTYPE_UNDO;
1039
1040         prop = RNA_def_boolean(ot->srna, "clear", 0, "Clear", "");
1041         RNA_def_property_flag(prop, PROP_HIDDEN | PROP_SKIP_SAVE);
1042
1043         WM_operatortype_props_advanced_begin(ot);
1044 }
1045
1046 /** \} */
1047
1048 /* -------------------------------------------------------------------- */
1049 /** \name Mark Edge (Sharp) Operator
1050  * \{ */
1051
1052 static int edbm_mark_sharp_exec(bContext *C, wmOperator *op)
1053 {
1054         BMEdge *eed;
1055         BMIter iter;
1056         const bool clear = RNA_boolean_get(op->ptr, "clear");
1057         const bool use_verts = RNA_boolean_get(op->ptr, "use_verts");
1058         ViewLayer *view_layer = CTX_data_view_layer(C);
1059
1060         uint objects_len = 0;
1061         Object **objects = BKE_view_layer_array_from_objects_in_edit_mode_unique_data(view_layer, &objects_len);
1062         for (uint ob_index = 0; ob_index < objects_len; ob_index++) {
1063                 Object *obedit = objects[ob_index];
1064                 BMEditMesh *em = BKE_editmesh_from_object(obedit);
1065                 BMesh *bm = em->bm;
1066                 Mesh *me = ((Mesh *)obedit->data);
1067
1068                 if (bm->totedgesel == 0) {
1069                         continue;
1070                 }
1071
1072                 /* auto-enable sharp edge drawing */
1073                 if (clear == 0) {
1074                         me->drawflag |= ME_DRAWSHARP;
1075                 }
1076
1077                 BM_ITER_MESH (eed, &iter, bm, BM_EDGES_OF_MESH) {
1078                         if (use_verts) {
1079                                 if (!(BM_elem_flag_test(eed->v1, BM_ELEM_SELECT) || BM_elem_flag_test(eed->v2, BM_ELEM_SELECT))) {
1080                                         continue;
1081                                 }
1082                         }
1083                         else if (!BM_elem_flag_test(eed, BM_ELEM_SELECT)) {
1084                                 continue;
1085                         }
1086
1087                         BM_elem_flag_set(eed, BM_ELEM_SMOOTH, clear);
1088                 }
1089
1090                 EDBM_update_generic(em, true, false);
1091         }
1092         MEM_freeN(objects);
1093
1094         return OPERATOR_FINISHED;
1095 }
1096
1097 void MESH_OT_mark_sharp(wmOperatorType *ot)
1098 {
1099         PropertyRNA *prop;
1100
1101         /* identifiers */
1102         ot->name = "Mark Sharp";
1103         ot->idname = "MESH_OT_mark_sharp";
1104         ot->description = "(Un)mark selected edges as sharp";
1105
1106         /* api callbacks */
1107         ot->exec = edbm_mark_sharp_exec;
1108         ot->poll = ED_operator_editmesh;
1109
1110         /* flags */
1111         ot->flag = OPTYPE_REGISTER | OPTYPE_UNDO;
1112
1113         prop = RNA_def_boolean(ot->srna, "clear", false, "Clear", "");
1114         RNA_def_property_flag(prop, PROP_HIDDEN | PROP_SKIP_SAVE);
1115         prop = RNA_def_boolean(ot->srna, "use_verts", false, "Vertices",
1116                                "Consider vertices instead of edges to select which edges to (un)tag as sharp");
1117         RNA_def_property_flag(prop, PROP_SKIP_SAVE);
1118 }
1119
1120 static bool edbm_connect_vert_pair(BMEditMesh *em, wmOperator *op)
1121 {
1122         BMesh *bm = em->bm;
1123         BMOperator bmop;
1124         const int verts_len = bm->totvertsel;
1125         bool is_pair = (verts_len == 2);
1126         int len = 0;
1127         bool check_degenerate = true;
1128
1129         BMVert **verts;
1130         bool checks_succeded = true;
1131
1132         /* sanity check */
1133         if (!is_pair) {
1134                 return false;
1135         }
1136
1137         verts = MEM_mallocN(sizeof(*verts) * verts_len, __func__);
1138         {
1139                 BMIter iter;
1140                 BMVert *v;
1141                 int i = 0;
1142
1143                 BM_ITER_MESH(v, &iter, bm, BM_VERTS_OF_MESH) {
1144                         if (BM_elem_flag_test(v, BM_ELEM_SELECT)) {
1145                                 verts[i++] = v;
1146                         }
1147                 }
1148
1149                 if (BM_vert_pair_share_face_check_cb(
1150                             verts[0], verts[1],
1151                             BM_elem_cb_check_hflag_disabled_simple(BMFace *, BM_ELEM_HIDDEN)))
1152                 {
1153                         check_degenerate = false;
1154                         is_pair = false;
1155                 }
1156         }
1157
1158         if (is_pair) {
1159                 if (!EDBM_op_init(
1160                             em, &bmop, op,
1161                             "connect_vert_pair verts=%eb verts_exclude=%hv faces_exclude=%hf",
1162                             verts, verts_len, BM_ELEM_HIDDEN, BM_ELEM_HIDDEN))
1163                 {
1164                         checks_succeded = false;
1165                 }
1166         }
1167         else {
1168                 if (!EDBM_op_init(
1169                             em, &bmop, op,
1170                             "connect_verts verts=%eb faces_exclude=%hf check_degenerate=%b",
1171                             verts, verts_len, BM_ELEM_HIDDEN, check_degenerate))
1172                 {
1173                         checks_succeded = false;
1174                 }
1175         }
1176         if (checks_succeded) {
1177                 BMO_op_exec(bm, &bmop);
1178                 len = BMO_slot_get(bmop.slots_out, "edges.out")->len;
1179
1180                 if (len && is_pair) {
1181                         /* new verts have been added, we have to select the edges, not just flush */
1182                         BMO_slot_buffer_hflag_enable(em->bm, bmop.slots_out, "edges.out", BM_EDGE, BM_ELEM_SELECT, true);
1183                 }
1184
1185                 if (!EDBM_op_finish(em, &bmop, op, true)) {
1186                         len = 0;
1187                 }
1188                 else {
1189                         EDBM_selectmode_flush(em);  /* so newly created edges get the selection state from the vertex */
1190
1191                         EDBM_update_generic(em, true, true);
1192                 }
1193         }
1194         MEM_freeN(verts);
1195
1196         return len;
1197 }
1198
1199 static int edbm_vert_connect_exec(bContext *C, wmOperator *op)
1200 {
1201         ViewLayer *view_layer = CTX_data_view_layer(C);
1202         uint objects_len = 0;
1203         uint failed_objects_len = 0;
1204         Object **objects = BKE_view_layer_array_from_objects_in_edit_mode_unique_data(view_layer, &objects_len);
1205
1206         for (uint ob_index = 0; ob_index < objects_len; ob_index++) {
1207                 Object *obedit = objects[ob_index];
1208                 BMEditMesh *em = BKE_editmesh_from_object(obedit);
1209
1210                 if (!edbm_connect_vert_pair(em, op)) {
1211                         failed_objects_len++;
1212                 }
1213         }
1214         MEM_freeN(objects);
1215         return failed_objects_len == objects_len ? OPERATOR_FINISHED : OPERATOR_CANCELLED;
1216 }
1217
1218 void MESH_OT_vert_connect(wmOperatorType *ot)
1219 {
1220         /* identifiers */
1221         ot->name = "Vertex Connect";
1222         ot->idname = "MESH_OT_vert_connect";
1223         ot->description = "Connect selected vertices of faces, splitting the face";
1224
1225         /* api callbacks */
1226         ot->exec = edbm_vert_connect_exec;
1227         ot->poll = ED_operator_editmesh;
1228
1229         /* flags */
1230         ot->flag = OPTYPE_REGISTER | OPTYPE_UNDO;
1231 }
1232
1233 /** \} */
1234
1235 /* -------------------------------------------------------------------- */
1236 /** \name Split Concave Faces Operator
1237  * \{ */
1238
1239 /**
1240  * check that endpoints are verts and only have a single selected edge connected.
1241  */
1242 static bool bm_vert_is_select_history_open(BMesh *bm)
1243 {
1244         BMEditSelection *ele_a = bm->selected.first;
1245         BMEditSelection *ele_b = bm->selected.last;
1246         if ((ele_a->htype == BM_VERT) &&
1247             (ele_b->htype == BM_VERT))
1248         {
1249                 if ((BM_iter_elem_count_flag(BM_EDGES_OF_VERT, (BMVert *)ele_a->ele, BM_ELEM_SELECT, true) == 1) &&
1250                     (BM_iter_elem_count_flag(BM_EDGES_OF_VERT, (BMVert *)ele_b->ele, BM_ELEM_SELECT, true) == 1))
1251                 {
1252                         return true;
1253                 }
1254         }
1255
1256         return false;
1257 }
1258
1259 static bool bm_vert_connect_pair(BMesh *bm, BMVert *v_a, BMVert *v_b)
1260 {
1261         BMOperator bmop;
1262         BMVert **verts;
1263         const int totedge_orig = bm->totedge;
1264
1265         BMO_op_init(bm, &bmop, BMO_FLAG_DEFAULTS, "connect_vert_pair");
1266
1267         verts = BMO_slot_buffer_alloc(&bmop, bmop.slots_in, "verts", 2);
1268         verts[0] = v_a;
1269         verts[1] = v_b;
1270
1271         BM_vert_normal_update(verts[0]);
1272         BM_vert_normal_update(verts[1]);
1273
1274         BMO_op_exec(bm, &bmop);
1275         BMO_slot_buffer_hflag_enable(bm, bmop.slots_out, "edges.out", BM_EDGE, BM_ELEM_SELECT, true);
1276         BMO_op_finish(bm, &bmop);
1277         return (bm->totedge != totedge_orig);
1278 }
1279
1280 static bool bm_vert_connect_select_history(BMesh *bm)
1281 {
1282         /* Logic is as follows:
1283          *
1284          * - If there are any isolated/wire verts - connect as edges.
1285          * - Otherwise connect faces.
1286          * - If all edges have been created already, closed the loop.
1287          */
1288         if (BLI_listbase_count_at_most(&bm->selected, 2) == 2 && (bm->totvertsel > 2)) {
1289                 BMEditSelection *ese;
1290                 int tot = 0;
1291                 bool changed = false;
1292                 bool has_wire = false;
1293                 // bool all_verts;
1294
1295                 /* ensure all verts have history */
1296                 for (ese = bm->selected.first; ese; ese = ese->next, tot++) {
1297                         BMVert *v;
1298                         if (ese->htype != BM_VERT) {
1299                                 break;
1300                         }
1301                         v = (BMVert *)ese->ele;
1302                         if ((has_wire == false) && ((v->e == NULL) || BM_vert_is_wire(v))) {
1303                                 has_wire = true;
1304                         }
1305                 }
1306                 // all_verts = (ese == NULL);
1307
1308                 if (has_wire == false) {
1309                         /* all verts have faces , connect verts via faces! */
1310                         if (tot == bm->totvertsel) {
1311                                 BMEditSelection *ese_last;
1312                                 ese_last = bm->selected.first;
1313                                 ese = ese_last->next;
1314
1315                                 do {
1316
1317                                         if (BM_edge_exists((BMVert *)ese_last->ele, (BMVert *)ese->ele)) {
1318                                                 /* pass, edge exists (and will be selected) */
1319                                         }
1320                                         else {
1321                                                 changed |= bm_vert_connect_pair(bm, (BMVert *)ese_last->ele, (BMVert *)ese->ele);
1322                                         }
1323                                 } while ((void)
1324                                          (ese_last = ese),
1325                                          (ese = ese->next));
1326
1327                                 if (changed) {
1328                                         return true;
1329                                 }
1330                         }
1331
1332                         if (changed == false) {
1333                                 /* existing loops: close the selection */
1334                                 if (bm_vert_is_select_history_open(bm)) {
1335                                         changed |= bm_vert_connect_pair(
1336                                                 bm,
1337                                                 (BMVert *)((BMEditSelection *)bm->selected.first)->ele,
1338                                                 (BMVert *)((BMEditSelection *)bm->selected.last)->ele);
1339
1340                                         if (changed) {
1341                                                 return true;
1342                                         }
1343                                 }
1344                         }
1345                 }
1346
1347                 else {
1348                         /* no faces, simply connect the verts by edges */
1349                         BMEditSelection *ese_prev;
1350                         ese_prev = bm->selected.first;
1351                         ese = ese_prev->next;
1352
1353
1354                         do {
1355                                 if (BM_edge_exists((BMVert *)ese_prev->ele, (BMVert *)ese->ele)) {
1356                                         /* pass, edge exists (and will be selected) */
1357                                 }
1358                                 else {
1359                                         BMEdge *e;
1360                                         e = BM_edge_create(bm, (BMVert *)ese_prev->ele, (BMVert *)ese->ele, NULL, 0);
1361                                         BM_edge_select_set(bm, e, true);
1362                                         changed = true;
1363                                 }
1364                         } while ((void)
1365                                  (ese_prev = ese),
1366                                  (ese = ese->next));
1367
1368                         if (changed == false) {
1369                                 /* existing loops: close the selection */
1370                                 if (bm_vert_is_select_history_open(bm)) {
1371                                         BMEdge *e;
1372                                         ese_prev = bm->selected.first;
1373                                         ese = bm->selected.last;
1374                                         e = BM_edge_create(bm, (BMVert *)ese_prev->ele, (BMVert *)ese->ele, NULL, 0);
1375                                         BM_edge_select_set(bm, e, true);
1376                                 }
1377                         }
1378
1379                         return true;
1380                 }
1381         }
1382
1383         return false;
1384 }
1385
1386 /**
1387  * Convert an edge selection to a temp vertex selection
1388  * (which must be cleared after use as a path to connect).
1389  */
1390 static bool bm_vert_connect_select_history_edge_to_vert_path(BMesh *bm, ListBase *r_selected)
1391 {
1392         ListBase selected_orig = {NULL, NULL};
1393         BMEditSelection *ese;
1394         int edges_len = 0;
1395         bool side = false;
1396
1397         /* first check all edges are OK */
1398         for (ese = bm->selected.first; ese; ese = ese->next) {
1399                 if (ese->htype == BM_EDGE) {
1400                         edges_len += 1;
1401                 }
1402                 else {
1403                         return false;
1404                 }
1405         }
1406         /* if this is a mixed selection, bail out! */
1407         if (bm->totedgesel != edges_len) {
1408                 return false;
1409         }
1410
1411         SWAP(ListBase, bm->selected, selected_orig);
1412
1413         /* convert edge selection into 2 ordered loops (where the first edge ends up in the middle) */
1414         for (ese = selected_orig.first; ese; ese = ese->next) {
1415                 BMEdge *e_curr = (BMEdge *)ese->ele;
1416                 BMEdge *e_prev = ese->prev ? (BMEdge *)ese->prev->ele : NULL;
1417                 BMLoop *l_curr;
1418                 BMLoop *l_prev;
1419                 BMVert *v;
1420
1421                 if (e_prev) {
1422                         BMFace *f = BM_edge_pair_share_face_by_len(e_curr, e_prev, &l_curr, &l_prev, true);
1423                         if (f) {
1424                                 if ((e_curr->v1 != l_curr->v) == (e_prev->v1 != l_prev->v)) {
1425                                         side = !side;
1426                                 }
1427                         }
1428                         else if (is_quad_flip_v3(e_curr->v1->co, e_curr->v2->co, e_prev->v2->co, e_prev->v1->co)) {
1429                                 side = !side;
1430                         }
1431                 }
1432
1433                 v = (&e_curr->v1)[side];
1434                 if (!bm->selected.last || (BMVert *)((BMEditSelection *)bm->selected.last)->ele != v) {
1435                         BM_select_history_store_notest(bm, v);
1436                 }
1437
1438                 v = (&e_curr->v1)[!side];
1439                 if (!bm->selected.first || (BMVert *)((BMEditSelection *)bm->selected.first)->ele != v) {
1440                         BM_select_history_store_head_notest(bm, v);
1441                 }
1442
1443                 e_prev = e_curr;
1444         }
1445
1446         *r_selected = bm->selected;
1447         bm->selected = selected_orig;
1448
1449         return true;
1450 }
1451
1452 static int edbm_vert_connect_path_exec(bContext *C, wmOperator *op)
1453 {
1454         ViewLayer *view_layer = CTX_data_view_layer(C);
1455         uint objects_len = 0;
1456         uint failed_selection_order_len = 0;
1457         uint failed_connect_len = 0;
1458         Object **objects = BKE_view_layer_array_from_objects_in_edit_mode_unique_data(view_layer, &objects_len);
1459
1460         for (uint ob_index = 0; ob_index < objects_len; ob_index++) {
1461                 Object *obedit = objects[ob_index];
1462                 BMEditMesh *em = BKE_editmesh_from_object(obedit);
1463                 BMesh *bm = em->bm;
1464                 const bool is_pair = (em->bm->totvertsel == 2);
1465                 ListBase selected_orig = {NULL, NULL};
1466
1467                 if (bm->totvertsel == 0) {
1468                         continue;
1469                 }
1470
1471                 /* when there is only 2 vertices, we can ignore selection order */
1472                 if (is_pair) {
1473                         if (!edbm_connect_vert_pair(em, op)) {
1474                                 failed_connect_len++;
1475                         }
1476                         continue;
1477                 }
1478
1479                 if (bm->selected.first) {
1480                         BMEditSelection *ese = bm->selected.first;
1481                         if (ese->htype == BM_EDGE) {
1482                                 if (bm_vert_connect_select_history_edge_to_vert_path(bm, &selected_orig)) {
1483                                         SWAP(ListBase, bm->selected, selected_orig);
1484                                 }
1485                         }
1486                 }
1487
1488                 if (bm_vert_connect_select_history(bm)) {
1489                         EDBM_selectmode_flush(em);
1490                         EDBM_update_generic(em, true, true);
1491                 }
1492                 else {
1493                         failed_selection_order_len++;
1494                 }
1495
1496                 if (!BLI_listbase_is_empty(&selected_orig)) {
1497                         BM_select_history_clear(bm);
1498                         bm->selected = selected_orig;
1499                 }
1500         }
1501
1502         MEM_freeN(objects);
1503
1504         if (failed_selection_order_len == objects_len) {
1505                 BKE_report(op->reports, RPT_ERROR, "Invalid selection order");
1506                 return OPERATOR_CANCELLED;
1507         }
1508         else if (failed_connect_len == objects_len) {
1509                 BKE_report(op->reports, RPT_ERROR, "Could not connect vertices");
1510                 return OPERATOR_CANCELLED;
1511         }
1512
1513         return OPERATOR_FINISHED;
1514 }
1515
1516 void MESH_OT_vert_connect_path(wmOperatorType *ot)
1517 {
1518         /* identifiers */
1519         ot->name = "Vertex Connect Path";
1520         ot->idname = "MESH_OT_vert_connect_path";
1521         ot->description = "Connect vertices by their selection order, creating edges, splitting faces";
1522
1523         /* api callbacks */
1524         ot->exec = edbm_vert_connect_path_exec;
1525         ot->poll = ED_operator_editmesh;
1526
1527         /* flags */
1528         ot->flag = OPTYPE_REGISTER | OPTYPE_UNDO;
1529 }
1530
1531 static int edbm_vert_connect_concave_exec(bContext *C, wmOperator *op)
1532 {
1533         ViewLayer *view_layer = CTX_data_view_layer(C);
1534         uint objects_len = 0;
1535         Object **objects = BKE_view_layer_array_from_objects_in_edit_mode_unique_data(view_layer, &objects_len);
1536         for (uint ob_index = 0; ob_index < objects_len; ob_index++) {
1537                 Object *obedit = objects[ob_index];
1538                 BMEditMesh *em = BKE_editmesh_from_object(obedit);
1539
1540                 if (em->bm->totfacesel == 0) {
1541                         continue;
1542                 }
1543
1544                 if (!EDBM_op_call_and_selectf(
1545                              em, op,
1546                              "faces.out", true,
1547                              "connect_verts_concave faces=%hf",
1548                              BM_ELEM_SELECT))
1549                 {
1550                         continue;
1551                 }
1552                 EDBM_update_generic(em, true, true);
1553         }
1554
1555         MEM_freeN(objects);
1556         return OPERATOR_FINISHED;
1557 }
1558
1559 void MESH_OT_vert_connect_concave(wmOperatorType *ot)
1560 {
1561         /* identifiers */
1562         ot->name = "Split Concave Faces";
1563         ot->idname = "MESH_OT_vert_connect_concave";
1564         ot->description = "Make all faces convex";
1565
1566         /* api callbacks */
1567         ot->exec = edbm_vert_connect_concave_exec;
1568         ot->poll = ED_operator_editmesh;
1569
1570         /* flags */
1571         ot->flag = OPTYPE_REGISTER | OPTYPE_UNDO;
1572 }
1573
1574 /** \} */
1575
1576 /* -------------------------------------------------------------------- */
1577 /** \name Split Non-Planar Faces Operator
1578  * \{ */
1579
1580 static int edbm_vert_connect_nonplaner_exec(bContext *C, wmOperator *op)
1581 {
1582         ViewLayer *view_layer = CTX_data_view_layer(C);
1583         const float angle_limit = RNA_float_get(op->ptr, "angle_limit");
1584         uint objects_len = 0;
1585         Object **objects = BKE_view_layer_array_from_objects_in_edit_mode_unique_data(view_layer, &objects_len);
1586
1587         for (uint ob_index = 0; ob_index < objects_len; ob_index++) {
1588                 Object *obedit = objects[ob_index];
1589                 BMEditMesh *em = BKE_editmesh_from_object(obedit);
1590
1591                 if (em->bm->totfacesel == 0) {
1592                         continue;
1593                 }
1594
1595                 if (!EDBM_op_call_and_selectf(
1596                             em, op,
1597                             "faces.out", true,
1598                             "connect_verts_nonplanar faces=%hf angle_limit=%f",
1599                             BM_ELEM_SELECT, angle_limit))
1600                 {
1601                         continue;
1602                 }
1603
1604                 EDBM_update_generic(em, true, true);
1605         }
1606         MEM_freeN(objects);
1607
1608         return OPERATOR_FINISHED;
1609 }
1610
1611 void MESH_OT_vert_connect_nonplanar(wmOperatorType *ot)
1612 {
1613         PropertyRNA *prop;
1614
1615         /* identifiers */
1616         ot->name = "Split Non-Planar Faces";
1617         ot->idname = "MESH_OT_vert_connect_nonplanar";
1618         ot->description = "Split non-planar faces that exceed the angle threshold";
1619
1620         /* api callbacks */
1621         ot->exec = edbm_vert_connect_nonplaner_exec;
1622         ot->poll = ED_operator_editmesh;
1623
1624         /* flags */
1625         ot->flag = OPTYPE_REGISTER | OPTYPE_UNDO;
1626
1627         /* props */
1628         prop = RNA_def_float_rotation(ot->srna, "angle_limit", 0, NULL, 0.0f, DEG2RADF(180.0f),
1629                                       "Max Angle", "Angle limit", 0.0f, DEG2RADF(180.0f));
1630         RNA_def_property_float_default(prop, DEG2RADF(5.0f));
1631 }
1632
1633 /** \} */
1634
1635 /* -------------------------------------------------------------------- */
1636 /** \name Make Planar Faces Operator
1637  * \{ */
1638
1639 static int edbm_face_make_planar_exec(bContext *C, wmOperator *op)
1640 {
1641         ViewLayer *view_layer = CTX_data_view_layer(C);
1642         uint objects_len = 0;
1643         Object **objects = BKE_view_layer_array_from_objects_in_edit_mode_unique_data(view_layer, &objects_len);
1644
1645         const int repeat = RNA_int_get(op->ptr, "repeat");
1646         const float fac = RNA_float_get(op->ptr, "factor");
1647
1648         for (uint ob_index = 0; ob_index < objects_len; ob_index++) {
1649                 Object *obedit = objects[ob_index];
1650                 BMEditMesh *em = BKE_editmesh_from_object(obedit);
1651                 if (em->bm->totfacesel == 0) {
1652                         continue;
1653                 }
1654
1655                 if (!EDBM_op_callf(
1656                             em, op, "planar_faces faces=%hf iterations=%i factor=%f",
1657                             BM_ELEM_SELECT, repeat, fac))
1658                 {
1659                         continue;
1660                 }
1661
1662                 EDBM_update_generic(em, true, true);
1663         }
1664         MEM_freeN(objects);
1665
1666         return OPERATOR_FINISHED;
1667 }
1668
1669 void MESH_OT_face_make_planar(wmOperatorType *ot)
1670 {
1671         /* identifiers */
1672         ot->name = "Make Planar Faces";
1673         ot->idname = "MESH_OT_face_make_planar";
1674         ot->description = "Flatten selected faces";
1675
1676         /* api callbacks */
1677         ot->exec = edbm_face_make_planar_exec;
1678         ot->poll = ED_operator_editmesh;
1679
1680         /* flags */
1681         ot->flag = OPTYPE_REGISTER | OPTYPE_UNDO;
1682
1683         /* props */
1684         RNA_def_float(ot->srna, "factor", 1.0f, -10.0f, 10.0f, "Factor", "", 0.0f, 1.0f);
1685         RNA_def_int(ot->srna, "repeat", 1, 1, 10000, "Iterations", "", 1, 200);
1686 }
1687
1688 /** \} */
1689
1690 /* -------------------------------------------------------------------- */
1691 /** \name Split Edge Operator
1692  * \{ */
1693
1694 static int edbm_edge_split_exec(bContext *C, wmOperator *op)
1695 {
1696         ViewLayer *view_layer = CTX_data_view_layer(C);
1697         uint objects_len = 0;
1698         Object **objects = BKE_view_layer_array_from_objects_in_edit_mode_unique_data(view_layer, &objects_len);
1699         for (uint ob_index = 0; ob_index < objects_len; ob_index++) {
1700                 Object *obedit = objects[ob_index];
1701                 BMEditMesh *em = BKE_editmesh_from_object(obedit);
1702                 if (em->bm->totedgesel == 0) {
1703                         continue;
1704                 }
1705
1706                 if (!EDBM_op_call_and_selectf(
1707                             em, op,
1708                             "edges.out", false,
1709                             "split_edges edges=%he",
1710                             BM_ELEM_SELECT))
1711                 {
1712                         continue;
1713                 }
1714
1715                 if (em->selectmode == SCE_SELECT_FACE) {
1716                         EDBM_select_flush(em);
1717                 }
1718
1719                 EDBM_update_generic(em, true, true);
1720         }
1721         MEM_freeN(objects);
1722
1723         return OPERATOR_FINISHED;
1724 }
1725
1726 void MESH_OT_edge_split(wmOperatorType *ot)
1727 {
1728         /* identifiers */
1729         ot->name = "Edge Split";
1730         ot->idname = "MESH_OT_edge_split";
1731         ot->description = "Split selected edges so that each neighbor face gets its own copy";
1732
1733         /* api callbacks */
1734         ot->exec = edbm_edge_split_exec;
1735         ot->poll = ED_operator_editmesh;
1736
1737         /* flags */
1738         ot->flag = OPTYPE_REGISTER | OPTYPE_UNDO;
1739 }
1740
1741 /** \} */
1742
1743 /* -------------------------------------------------------------------- */
1744 /** \name Duplicate Operator
1745  * \{ */
1746
1747 static int edbm_duplicate_exec(bContext *C, wmOperator *op)
1748 {
1749         ViewLayer *view_layer = CTX_data_view_layer(C);
1750         uint objects_len = 0;
1751         Object **objects = BKE_view_layer_array_from_objects_in_edit_mode_unique_data(view_layer, &objects_len);
1752
1753         for (uint ob_index = 0; ob_index < objects_len; ob_index++) {
1754                 Object *obedit = objects[ob_index];
1755                 BMEditMesh *em = BKE_editmesh_from_object(obedit);
1756                 if (em->bm->totvertsel == 0) {
1757                         continue;
1758                 }
1759
1760                 BMOperator bmop;
1761                 BMesh *bm = em->bm;
1762
1763                 EDBM_op_init(
1764                         em, &bmop, op,
1765                         "duplicate geom=%hvef use_select_history=%b",
1766                         BM_ELEM_SELECT, true);
1767
1768                 BMO_op_exec(bm, &bmop);
1769
1770                 /* de-select all would clear otherwise */
1771                 BM_SELECT_HISTORY_BACKUP(bm);
1772
1773                 EDBM_flag_disable_all(em, BM_ELEM_SELECT);
1774
1775                 BMO_slot_buffer_hflag_enable(bm, bmop.slots_out, "geom.out", BM_ALL_NOLOOP, BM_ELEM_SELECT, true);
1776
1777                 /* rebuild editselection */
1778                 BM_SELECT_HISTORY_RESTORE(bm);
1779
1780                 if (!EDBM_op_finish(em, &bmop, op, true)) {
1781                         continue;
1782                 }
1783                 EDBM_update_generic(em, true, true);
1784         }
1785         MEM_freeN(objects);
1786
1787         return OPERATOR_FINISHED;
1788 }
1789
1790 static int edbm_duplicate_invoke(bContext *C, wmOperator *op, const wmEvent *UNUSED(event))
1791 {
1792         WM_cursor_wait(1);
1793         edbm_duplicate_exec(C, op);
1794         WM_cursor_wait(0);
1795
1796         return OPERATOR_FINISHED;
1797 }
1798
1799 void MESH_OT_duplicate(wmOperatorType *ot)
1800 {
1801         /* identifiers */
1802         ot->name = "Duplicate";
1803         ot->description = "Duplicate selected vertices, edges or faces";
1804         ot->idname = "MESH_OT_duplicate";
1805
1806         /* api callbacks */
1807         ot->invoke = edbm_duplicate_invoke;
1808         ot->exec = edbm_duplicate_exec;
1809
1810         ot->poll = ED_operator_editmesh;
1811
1812         /* to give to transform */
1813         RNA_def_int(ot->srna, "mode", TFM_TRANSLATION, 0, INT_MAX, "Mode", "", 0, INT_MAX);
1814 }
1815
1816 /** \} */
1817
1818 /* -------------------------------------------------------------------- */
1819 /** \name Flip Normals Operator
1820  * \{ */
1821 static int edbm_flip_normals_exec(bContext *C, wmOperator *op)
1822 {
1823         ViewLayer *view_layer = CTX_data_view_layer(C);
1824         uint objects_len = 0;
1825         Object **objects = BKE_view_layer_array_from_objects_in_edit_mode_unique_data(view_layer, &objects_len);
1826
1827         for (uint ob_index = 0; ob_index < objects_len; ob_index++) {
1828                 Object *obedit = objects[ob_index];
1829                 BMEditMesh *em = BKE_editmesh_from_object(obedit);
1830
1831                 if (em->bm->totfacesel == 0) {
1832                         continue;
1833                 }
1834
1835                 if (!EDBM_op_callf(
1836                         em, op, "reverse_faces faces=%hf flip_multires=%b",
1837                         BM_ELEM_SELECT, true))
1838                 {
1839                         continue;
1840                 }
1841
1842                 EDBM_update_generic(em, true, false);
1843         }
1844
1845         MEM_freeN(objects);
1846         return OPERATOR_FINISHED;
1847 }
1848
1849 void MESH_OT_flip_normals(wmOperatorType *ot)
1850 {
1851         /* identifiers */
1852         ot->name = "Flip Normals";
1853         ot->description = "Flip the direction of selected faces' normals (and of their vertices)";
1854         ot->idname = "MESH_OT_flip_normals";
1855
1856         /* api callbacks */
1857         ot->exec = edbm_flip_normals_exec;
1858         ot->poll = ED_operator_editmesh;
1859
1860         /* flags */
1861         ot->flag = OPTYPE_REGISTER | OPTYPE_UNDO;
1862 }
1863
1864 /** \} */
1865
1866 /* -------------------------------------------------------------------- */
1867 /** \name Rotate Edge Operator
1868  * \{ */
1869
1870 /**
1871  * Rotate the edges between selected faces, otherwise rotate the selected edges.
1872  */
1873 static int edbm_edge_rotate_selected_exec(bContext *C, wmOperator *op)
1874 {
1875         BMEdge *eed;
1876         BMIter iter;
1877         const bool use_ccw = RNA_boolean_get(op->ptr, "use_ccw");
1878
1879         int tot_rotate_all = 0, tot_failed_all = 0;
1880         bool no_selected_edges = true, invalid_selected_edges = true;
1881
1882         ViewLayer *view_layer = CTX_data_view_layer(C);
1883         uint objects_len = 0;
1884         Object **objects = BKE_view_layer_array_from_objects_in_edit_mode_unique_data(view_layer, &objects_len);
1885         for (uint ob_index = 0; ob_index < objects_len; ob_index++) {
1886                 Object *obedit = objects[ob_index];
1887                 BMEditMesh *em = BKE_editmesh_from_object(obedit);
1888                 int tot = 0;
1889
1890                 if (em->bm->totedgesel == 0) {
1891                         continue;
1892                 }
1893                 no_selected_edges = false;
1894
1895                 /* first see if we have two adjacent faces */
1896                 BM_ITER_MESH (eed, &iter, em->bm, BM_EDGES_OF_MESH) {
1897                         BM_elem_flag_disable(eed, BM_ELEM_TAG);
1898                         if (BM_elem_flag_test(eed, BM_ELEM_SELECT)) {
1899                                 BMFace *fa, *fb;
1900                                 if (BM_edge_face_pair(eed, &fa, &fb)) {
1901                                         /* if both faces are selected we rotate between them,
1902                                          * otherwise - rotate between 2 unselected - but not mixed */
1903                                         if (BM_elem_flag_test(fa, BM_ELEM_SELECT) == BM_elem_flag_test(fb, BM_ELEM_SELECT)) {
1904                                                 BM_elem_flag_enable(eed, BM_ELEM_TAG);
1905                                                 tot++;
1906                                         }
1907                                 }
1908                         }
1909                 }
1910
1911                 /* ok, we don't have two adjacent faces, but we do have two selected ones.
1912                  * that's an error condition.*/
1913                 if (tot == 0) {
1914                         continue;
1915                 }
1916                 invalid_selected_edges = false;
1917
1918                 BMOperator bmop;
1919                 EDBM_op_init(em, &bmop, op, "rotate_edges edges=%he use_ccw=%b", BM_ELEM_TAG, use_ccw);
1920
1921                 /* avoids leaving old verts selected which can be a problem running multiple times,
1922                  * since this means the edges become selected around the face which then attempt to rotate */
1923                 BMO_slot_buffer_hflag_disable(em->bm, bmop.slots_in, "edges", BM_EDGE, BM_ELEM_SELECT, true);
1924
1925                 BMO_op_exec(em->bm, &bmop);
1926                 /* edges may rotate into hidden vertices, if this does _not_ run we get an ilogical state */
1927                 BMO_slot_buffer_hflag_disable(em->bm, bmop.slots_out, "edges.out", BM_EDGE, BM_ELEM_HIDDEN, true);
1928                 BMO_slot_buffer_hflag_enable(em->bm, bmop.slots_out, "edges.out", BM_EDGE, BM_ELEM_SELECT, true);
1929
1930                 const int tot_rotate = BMO_slot_buffer_count(bmop.slots_out, "edges.out");
1931                 const int tot_failed = tot - tot_rotate;
1932
1933                 tot_rotate_all += tot_rotate;
1934                 tot_failed_all += tot_failed;
1935
1936                 if (tot_failed != 0) {
1937                         /* If some edges fail to rotate, we need to re-select them,
1938                          * otherwise we can end up with invalid selection
1939                          * (unselected edge between 2 selected faces). */
1940                         BM_mesh_elem_hflag_enable_test(em->bm, BM_EDGE, BM_ELEM_SELECT, true, false, BM_ELEM_TAG);
1941                 }
1942
1943                 EDBM_selectmode_flush(em);
1944
1945                 if (!EDBM_op_finish(em, &bmop, op, true)) {
1946                         continue;
1947                 }
1948
1949                 EDBM_update_generic(em, true, true);
1950         }
1951         MEM_freeN(objects);
1952
1953         if (no_selected_edges) {
1954                 BKE_report(op->reports, RPT_ERROR, "Select edges or face pairs for edge loops to rotate about");
1955                 return OPERATOR_CANCELLED;
1956         }
1957
1958         /* Ok, we don't have two adjacent faces, but we do have two selected ones.
1959          * that's an error condition. */
1960         if (invalid_selected_edges) {
1961                 BKE_report(op->reports, RPT_ERROR, "Could not find any selected edges that can be rotated");
1962                 return OPERATOR_CANCELLED;
1963         }
1964
1965         if (tot_failed_all != 0) {
1966                 BKE_reportf(op->reports, RPT_WARNING, "Unable to rotate %d edge(s)", tot_failed_all);
1967         }
1968
1969         return OPERATOR_FINISHED;
1970 }
1971
1972 void MESH_OT_edge_rotate(wmOperatorType *ot)
1973 {
1974         /* identifiers */
1975         ot->name = "Rotate Selected Edge";
1976         ot->description = "Rotate selected edge or adjoining faces";
1977         ot->idname = "MESH_OT_edge_rotate";
1978
1979         /* api callbacks */
1980         ot->exec = edbm_edge_rotate_selected_exec;
1981         ot->poll = ED_operator_editmesh;
1982
1983         /* flags */
1984         ot->flag = OPTYPE_REGISTER | OPTYPE_UNDO;
1985
1986         /* props */
1987         RNA_def_boolean(ot->srna, "use_ccw", false, "Counter Clockwise", "");
1988 }
1989
1990 /** \} */
1991
1992 /* -------------------------------------------------------------------- */
1993 /** \name Hide Operator
1994  * \{ */
1995
1996 static int edbm_hide_exec(bContext *C, wmOperator *op)
1997 {
1998         const bool unselected = RNA_boolean_get(op->ptr, "unselected");
1999         ViewLayer *view_layer = CTX_data_view_layer(C);
2000
2001         uint objects_len = 0;
2002         Object **objects = BKE_view_layer_array_from_objects_in_edit_mode_unique_data(view_layer, &objects_len);
2003         for (uint ob_index = 0; ob_index < objects_len; ob_index++) {
2004                 Object *obedit = objects[ob_index];
2005                 BMEditMesh *em = BKE_editmesh_from_object(obedit);
2006                 BMesh *bm = em->bm;
2007
2008                 if ((bm->totvertsel == 0) &&
2009                     (bm->totedgesel == 0) &&
2010                     (bm->totfacesel == 0))
2011                 {
2012                         continue;
2013                 }
2014
2015                 EDBM_mesh_hide(em, unselected);
2016                 EDBM_update_generic(em, true, false);
2017         }
2018
2019         MEM_freeN(objects);
2020         return OPERATOR_FINISHED;
2021 }
2022
2023 void MESH_OT_hide(wmOperatorType *ot)
2024 {
2025         /* identifiers */
2026         ot->name = "Hide Selection";
2027         ot->idname = "MESH_OT_hide";
2028         ot->description = "Hide (un)selected vertices, edges or faces";
2029
2030         /* api callbacks */
2031         ot->exec = edbm_hide_exec;
2032         ot->poll = ED_operator_editmesh;
2033
2034         /* flags */
2035         ot->flag = OPTYPE_REGISTER | OPTYPE_UNDO;
2036
2037         /* props */
2038         RNA_def_boolean(ot->srna, "unselected", false, "Unselected", "Hide unselected rather than selected");
2039 }
2040
2041 /** \} */
2042
2043 /* -------------------------------------------------------------------- */
2044 /** \name Reveal Operator
2045  * \{ */
2046
2047 static int edbm_reveal_exec(bContext *C, wmOperator *op)
2048 {
2049         const bool select = RNA_boolean_get(op->ptr, "select");
2050         ViewLayer *view_layer = CTX_data_view_layer(C);
2051
2052         uint objects_len = 0;
2053         Object **objects = BKE_view_layer_array_from_objects_in_edit_mode_unique_data(view_layer, &objects_len);
2054         for (uint ob_index = 0; ob_index < objects_len; ob_index++) {
2055                 Object *obedit = objects[ob_index];
2056                 BMEditMesh *em = BKE_editmesh_from_object(obedit);
2057
2058                 EDBM_mesh_reveal(em, select);
2059                 EDBM_update_generic(em, true, false);
2060         }
2061         MEM_freeN(objects);
2062
2063         return OPERATOR_FINISHED;
2064 }
2065
2066 void MESH_OT_reveal(wmOperatorType *ot)
2067 {
2068         /* identifiers */
2069         ot->name = "Reveal Hidden";
2070         ot->idname = "MESH_OT_reveal";
2071         ot->description = "Reveal all hidden vertices, edges and faces";
2072
2073         /* api callbacks */
2074         ot->exec = edbm_reveal_exec;
2075         ot->poll = ED_operator_editmesh;
2076
2077         /* flags */
2078         ot->flag = OPTYPE_REGISTER | OPTYPE_UNDO;
2079
2080         RNA_def_boolean(ot->srna, "select", true, "Select", "");
2081 }
2082
2083 /** \} */
2084
2085 /* -------------------------------------------------------------------- */
2086 /** \name Recalculate Normals Operator
2087  * \{ */
2088
2089 static int edbm_normals_make_consistent_exec(bContext *C, wmOperator *op)
2090 {
2091         ViewLayer *view_layer = CTX_data_view_layer(C);
2092
2093         uint objects_len = 0;
2094         Object **objects = BKE_view_layer_array_from_objects_in_edit_mode_unique_data(view_layer, &objects_len);
2095         for (uint ob_index = 0; ob_index < objects_len; ob_index++) {
2096                 Object *obedit = objects[ob_index];
2097                 BMEditMesh *em = BKE_editmesh_from_object(obedit);
2098
2099                 if (em->bm->totfacesel == 0) {
2100                         continue;
2101                 }
2102
2103                 if (!EDBM_op_callf(em, op, "recalc_face_normals faces=%hf", BM_ELEM_SELECT)) {
2104                         continue;
2105                 }
2106                 if (RNA_boolean_get(op->ptr, "inside")) {
2107                         EDBM_op_callf(em, op, "reverse_faces faces=%hf flip_multires=%b", BM_ELEM_SELECT, true);
2108                 }
2109
2110                 EDBM_update_generic(em, true, false);
2111         }
2112         MEM_freeN(objects);
2113
2114         return OPERATOR_FINISHED;
2115 }
2116
2117 void MESH_OT_normals_make_consistent(wmOperatorType *ot)
2118 {
2119         /* identifiers */
2120         ot->name = "Make Normals Consistent";
2121         ot->description = "Make face and vertex normals point either outside or inside the mesh";
2122         ot->idname = "MESH_OT_normals_make_consistent";
2123
2124         /* api callbacks */
2125         ot->exec = edbm_normals_make_consistent_exec;
2126         ot->poll = ED_operator_editmesh;
2127
2128         /* flags */
2129         ot->flag = OPTYPE_REGISTER | OPTYPE_UNDO;
2130
2131         RNA_def_boolean(ot->srna, "inside", false, "Inside", "");
2132 }
2133
2134 /** \} */
2135
2136 /* -------------------------------------------------------------------- */
2137 /** \name Smooth Vertex Operator
2138  * \{ */
2139
2140 static int edbm_do_smooth_vertex_exec(bContext *C, wmOperator *op)
2141 {
2142         const float fac = RNA_float_get(op->ptr, "factor");
2143
2144         const bool xaxis = RNA_boolean_get(op->ptr, "xaxis");
2145         const bool yaxis = RNA_boolean_get(op->ptr, "yaxis");
2146         const bool zaxis = RNA_boolean_get(op->ptr, "zaxis");
2147         int repeat = RNA_int_get(op->ptr, "repeat");
2148
2149         if (!repeat) {
2150                 repeat = 1;
2151         }
2152
2153         ViewLayer *view_layer = CTX_data_view_layer(C);
2154         uint objects_len = 0;
2155         Object **objects = BKE_view_layer_array_from_objects_in_edit_mode_unique_data(view_layer, &objects_len);
2156         for (uint ob_index = 0; ob_index < objects_len; ob_index++) {
2157                 Object *obedit = objects[ob_index];
2158                 Mesh *me = obedit->data;
2159                 BMEditMesh *em = BKE_editmesh_from_object(obedit);
2160                 ModifierData *md;
2161                 bool mirrx = false, mirry = false, mirrz = false;
2162                 int i;
2163                 float clip_dist = 0.0f;
2164                 const bool use_topology = (me->editflag & ME_EDIT_MIRROR_TOPO) != 0;
2165
2166                 if (em->bm->totvertsel == 0) {
2167                         continue;
2168                 }
2169
2170                 /* mirror before smooth */
2171                 if (((Mesh *)obedit->data)->editflag & ME_EDIT_MIRROR_X) {
2172                         EDBM_verts_mirror_cache_begin(em, 0, false, true, use_topology);
2173                 }
2174
2175                 /* if there is a mirror modifier with clipping, flag the verts that
2176                  * are within tolerance of the plane(s) of reflection
2177                  */
2178                 for (md = obedit->modifiers.first; md; md = md->next) {
2179                         if (md->type == eModifierType_Mirror && (md->mode & eModifierMode_Realtime)) {
2180                                 MirrorModifierData *mmd = (MirrorModifierData *)md;
2181
2182                                 if (mmd->flag & MOD_MIR_CLIPPING) {
2183                                         if (mmd->flag & MOD_MIR_AXIS_X)
2184                                                 mirrx = true;
2185                                         if (mmd->flag & MOD_MIR_AXIS_Y)
2186                                                 mirry = true;
2187                                         if (mmd->flag & MOD_MIR_AXIS_Z)
2188                                                 mirrz = true;
2189
2190                                         clip_dist = mmd->tolerance;
2191                                 }
2192                         }
2193                 }
2194
2195                 for (i = 0; i < repeat; i++) {
2196                         if (!EDBM_op_callf(
2197                                 em, op,
2198                                 "smooth_vert verts=%hv factor=%f mirror_clip_x=%b mirror_clip_y=%b mirror_clip_z=%b "
2199                                 "clip_dist=%f use_axis_x=%b use_axis_y=%b use_axis_z=%b",
2200                                 BM_ELEM_SELECT, fac, mirrx, mirry, mirrz, clip_dist, xaxis, yaxis, zaxis))
2201                         {
2202                                 continue;
2203                         }
2204                 }
2205
2206                 /* apply mirror */
2207                 if (((Mesh *)obedit->data)->editflag & ME_EDIT_MIRROR_X) {
2208                         EDBM_verts_mirror_apply(em, BM_ELEM_SELECT, 0);
2209                         EDBM_verts_mirror_cache_end(em);
2210                 }
2211
2212                 EDBM_update_generic(em, true, false);
2213         }
2214         MEM_freeN(objects);
2215
2216         return OPERATOR_FINISHED;
2217 }
2218
2219 void MESH_OT_vertices_smooth(wmOperatorType *ot)
2220 {
2221         /* identifiers */
2222         ot->name = "Smooth Vertex";
2223         ot->description = "Flatten angles of selected vertices";
2224         ot->idname = "MESH_OT_vertices_smooth";
2225
2226         /* api callbacks */
2227         ot->exec = edbm_do_smooth_vertex_exec;
2228         ot->poll = ED_operator_editmesh;
2229
2230         /* flags */
2231         ot->flag = OPTYPE_REGISTER | OPTYPE_UNDO;
2232
2233         RNA_def_float(ot->srna, "factor", 0.5f, -10.0f, 10.0f, "Smoothing", "Smoothing factor", 0.0f, 1.0f);
2234         RNA_def_int(ot->srna, "repeat", 1, 1, 1000, "Repeat", "Number of times to smooth the mesh", 1, 100);
2235
2236         WM_operatortype_props_advanced_begin(ot);
2237
2238         RNA_def_boolean(ot->srna, "xaxis", true, "X-Axis", "Smooth along the X axis");
2239         RNA_def_boolean(ot->srna, "yaxis", true, "Y-Axis", "Smooth along the Y axis");
2240         RNA_def_boolean(ot->srna, "zaxis", true, "Z-Axis", "Smooth along the Z axis");
2241 }
2242
2243 /** \} */
2244
2245 /* -------------------------------------------------------------------- */
2246 /** \name Laplacian Vertex Smooth Operator
2247  * \{ */
2248
2249 static int edbm_do_smooth_laplacian_vertex_exec(bContext *C, wmOperator *op)
2250 {
2251         BMIter fiter;
2252         BMFace *f;
2253         int tot_invalid = 0;
2254         int tot_unselected = 0;
2255         ViewLayer *view_layer = CTX_data_view_layer(C);
2256
2257         const float lambda_factor = RNA_float_get(op->ptr, "lambda_factor");
2258         const float lambda_border = RNA_float_get(op->ptr, "lambda_border");
2259         const bool usex = RNA_boolean_get(op->ptr, "use_x");
2260         const bool usey = RNA_boolean_get(op->ptr, "use_y");
2261         const bool usez = RNA_boolean_get(op->ptr, "use_z");
2262         const bool preserve_volume = RNA_boolean_get(op->ptr, "preserve_volume");
2263         int repeat = RNA_int_get(op->ptr, "repeat");
2264
2265         if (!repeat) {
2266                 repeat = 1;
2267         }
2268
2269         uint objects_len = 0;
2270         Object **objects = BKE_view_layer_array_from_objects_in_edit_mode_unique_data(view_layer, &objects_len);
2271         for (uint ob_index = 0; ob_index < objects_len; ob_index++) {
2272                 Object *obedit = objects[ob_index];
2273                 BMEditMesh *em = BKE_editmesh_from_object(obedit);
2274                 Mesh *me = obedit->data;
2275                 bool use_topology = (me->editflag & ME_EDIT_MIRROR_TOPO) != 0;
2276
2277                 if (em->bm->totvertsel == 0) {
2278                         tot_unselected++;
2279                         tot_invalid++;
2280                         continue;
2281                 }
2282
2283                 bool is_invalid = false;
2284                 /* Check if select faces are triangles. */
2285                 BM_ITER_MESH (f, &fiter, em->bm, BM_FACES_OF_MESH) {
2286                         if (BM_elem_flag_test(f, BM_ELEM_SELECT)) {
2287                                 if (f->len > 4) {
2288                                         tot_invalid++;
2289                                         is_invalid = true;
2290                                         break;
2291                                 }
2292                         }
2293                 }
2294                 if (is_invalid) {
2295                         continue;
2296                 }
2297
2298                 /* Mirror before smooth. */
2299                 if (((Mesh *)obedit->data)->editflag & ME_EDIT_MIRROR_X) {
2300                         EDBM_verts_mirror_cache_begin(em, 0, false, true, use_topology);
2301                 }
2302
2303                 bool failed_repeat_loop = false;
2304                 for (int i = 0; i < repeat; i++) {
2305                         if (!EDBM_op_callf(
2306                                 em, op,
2307                                 "smooth_laplacian_vert verts=%hv lambda_factor=%f lambda_border=%f use_x=%b use_y=%b use_z=%b preserve_volume=%b",
2308                                 BM_ELEM_SELECT, lambda_factor, lambda_border, usex, usey, usez, preserve_volume))
2309                         {
2310                                 failed_repeat_loop = true;
2311                                 break;
2312                         }
2313                 }
2314                 if (failed_repeat_loop) {
2315                         continue;
2316                 }
2317
2318                 /* Apply mirror. */
2319                 if (((Mesh *)obedit->data)->editflag & ME_EDIT_MIRROR_X) {
2320                         EDBM_verts_mirror_apply(em, BM_ELEM_SELECT, 0);
2321                         EDBM_verts_mirror_cache_end(em);
2322                 }
2323
2324                 EDBM_update_generic(em, true, false);
2325         }
2326         MEM_freeN(objects);
2327
2328         if (tot_unselected == objects_len) {
2329                 BKE_report(op->reports, RPT_WARNING, "No selected vertex");
2330                 return OPERATOR_CANCELLED;
2331         }
2332         else if (tot_invalid == objects_len) {
2333                 BKE_report(op->reports, RPT_WARNING, "Selected faces must be triangles or quads");
2334                 return OPERATOR_CANCELLED;
2335         }
2336
2337         return OPERATOR_FINISHED;
2338 }
2339
2340 void MESH_OT_vertices_smooth_laplacian(wmOperatorType *ot)
2341 {
2342         /* identifiers */
2343         ot->name = "Laplacian Smooth Vertex";
2344         ot->description = "Laplacian smooth of selected vertices";
2345         ot->idname = "MESH_OT_vertices_smooth_laplacian";
2346
2347         /* api callbacks */
2348         ot->exec = edbm_do_smooth_laplacian_vertex_exec;
2349         ot->poll = ED_operator_editmesh;
2350
2351         /* flags */
2352         ot->flag = OPTYPE_REGISTER | OPTYPE_UNDO;
2353
2354         RNA_def_int(ot->srna, "repeat", 1, 1, 1000,
2355                     "Number of iterations to smooth the mesh", "", 1, 200);
2356         RNA_def_float(ot->srna, "lambda_factor", 1.0f, 1e-7f, 1000.0f,
2357                       "Lambda factor", "", 1e-7f, 1000.0f);
2358         RNA_def_float(ot->srna, "lambda_border", 5e-5f, 1e-7f, 1000.0f,
2359                       "Lambda factor in border", "", 1e-7f, 1000.0f);
2360
2361         WM_operatortype_props_advanced_begin(ot);
2362
2363         RNA_def_boolean(ot->srna, "use_x", true, "Smooth X Axis", "Smooth object along X axis");
2364         RNA_def_boolean(ot->srna, "use_y", true, "Smooth Y Axis", "Smooth object along Y axis");
2365         RNA_def_boolean(ot->srna, "use_z", true, "Smooth Z Axis", "Smooth object along Z axis");
2366         RNA_def_boolean(ot->srna, "preserve_volume", true, "Preserve Volume", "Apply volume preservation after smooth");
2367 }
2368
2369 /** \} */
2370
2371 /* -------------------------------------------------------------------- */
2372 /** \name Set Faces Smooth Shading Operator
2373  * \{ */
2374
2375 static void mesh_set_smooth_faces(BMEditMesh *em, short smooth)
2376 {
2377         BMIter iter;
2378         BMFace *efa;
2379
2380         if (em == NULL) return;
2381
2382         BM_ITER_MESH (efa, &iter, em->bm, BM_FACES_OF_MESH) {
2383                 if (BM_elem_flag_test(efa, BM_ELEM_SELECT)) {
2384                         BM_elem_flag_set(efa, BM_ELEM_SMOOTH, smooth);
2385                 }
2386         }
2387 }
2388
2389 static int edbm_faces_shade_smooth_exec(bContext *C, wmOperator *UNUSED(op))
2390 {
2391         ViewLayer * view_layer = CTX_data_view_layer(C);
2392         uint objects_len = 0;
2393         Object * *objects = BKE_view_layer_array_from_objects_in_edit_mode_unique_data(view_layer, &objects_len);
2394         for (uint ob_index = 0; ob_index < objects_len; ob_index++) {
2395                 Object * obedit = objects[ob_index];
2396                 BMEditMesh * em = BKE_editmesh_from_object(obedit);
2397
2398                 if (em->bm->totfacesel == 0) {
2399                         continue;
2400                 }
2401
2402                 mesh_set_smooth_faces(em, 1);
2403                 EDBM_update_generic(em, false, false);
2404         }
2405         MEM_freeN(objects);
2406
2407         return OPERATOR_FINISHED;
2408 }
2409
2410 void MESH_OT_faces_shade_smooth(wmOperatorType *ot)
2411 {
2412         /* identifiers */
2413         ot->name = "Shade Smooth";
2414         ot->description = "Display faces smooth (using vertex normals)";
2415         ot->idname = "MESH_OT_faces_shade_smooth";
2416
2417         /* api callbacks */
2418         ot->exec = edbm_faces_shade_smooth_exec;
2419         ot->poll = ED_operator_editmesh;
2420
2421         /* flags */
2422         ot->flag = OPTYPE_REGISTER | OPTYPE_UNDO;
2423 }
2424
2425 /** \} */
2426
2427 /* -------------------------------------------------------------------- */
2428 /** \name Set Faces Flat Shading Operator
2429  * \{ */
2430
2431 static int edbm_faces_shade_flat_exec(bContext *C, wmOperator *UNUSED(op))
2432 {
2433         ViewLayer *view_layer = CTX_data_view_layer(C);
2434         uint objects_len = 0;
2435         Object **objects = BKE_view_layer_array_from_objects_in_edit_mode_unique_data(view_layer, &objects_len);
2436         for (uint ob_index = 0; ob_index < objects_len; ob_index++) {
2437                 Object *obedit = objects[ob_index];
2438                 BMEditMesh *em = BKE_editmesh_from_object(obedit);
2439
2440                 if (em->bm->totfacesel == 0) {
2441                         continue;
2442                 }
2443
2444                 mesh_set_smooth_faces(em, 0);
2445                 EDBM_update_generic(em, false, false);
2446         }
2447         MEM_freeN(objects);
2448
2449         return OPERATOR_FINISHED;
2450 }
2451
2452 void MESH_OT_faces_shade_flat(wmOperatorType *ot)
2453 {
2454         /* identifiers */
2455         ot->name = "Shade Flat";
2456         ot->description = "Display faces flat";
2457         ot->idname = "MESH_OT_faces_shade_flat";
2458
2459         /* api callbacks */
2460         ot->exec = edbm_faces_shade_flat_exec;
2461         ot->poll = ED_operator_editmesh;
2462
2463         /* flags */
2464         ot->flag = OPTYPE_REGISTER | OPTYPE_UNDO;
2465 }
2466
2467 /** \} */
2468
2469 /* -------------------------------------------------------------------- */
2470 /** \name UV/Color Rotate/Reverse Operator
2471  * \{ */
2472
2473 static int edbm_rotate_uvs_exec(bContext *C, wmOperator *op)
2474 {
2475         /* get the direction from RNA */
2476         const bool use_ccw = RNA_boolean_get(op->ptr, "use_ccw");
2477
2478         ViewLayer *view_layer = CTX_data_view_layer(C);
2479         uint objects_len = 0;
2480         Object **objects = BKE_view_layer_array_from_objects_in_edit_mode_unique_data(view_layer, &objects_len);
2481         for (uint ob_index = 0; ob_index < objects_len; ob_index++) {
2482                 Object *obedit = objects[ob_index];
2483                 BMEditMesh *em = BKE_editmesh_from_object(obedit);
2484
2485                 if (em->bm->totfacesel == 0) {
2486                         continue;
2487                 }
2488
2489                 BMOperator bmop;
2490
2491                 /* initialize the bmop using EDBM api, which does various ui error reporting and other stuff */
2492                 EDBM_op_init(em, &bmop, op, "rotate_uvs faces=%hf use_ccw=%b", BM_ELEM_SELECT, use_ccw);
2493
2494                 /* execute the operator */
2495                 BMO_op_exec(em->bm, &bmop);
2496
2497                 if (!EDBM_op_finish(em, &bmop, op, true)) {
2498                         continue;
2499                 }
2500
2501                 EDBM_update_generic(em, false, false);
2502         }
2503
2504         MEM_freeN(objects);
2505         return OPERATOR_FINISHED;
2506 }
2507
2508 static int edbm_reverse_uvs_exec(bContext *C, wmOperator *op)
2509 {
2510         ViewLayer *view_layer = CTX_data_view_layer(C);
2511         uint objects_len = 0;
2512         Object **objects = BKE_view_layer_array_from_objects_in_edit_mode_unique_data(view_layer, &objects_len);
2513         for (uint ob_index = 0; ob_index < objects_len; ob_index++) {
2514                 Object *obedit = objects[ob_index];
2515                 BMEditMesh *em = BKE_editmesh_from_object(obedit);
2516
2517                 if (em->bm->totfacesel == 0) {
2518                         continue;
2519                 }
2520
2521                 BMOperator bmop;
2522
2523                 /* initialize the bmop using EDBM api, which does various ui error reporting and other stuff */
2524                 EDBM_op_init(em, &bmop, op, "reverse_uvs faces=%hf", BM_ELEM_SELECT);
2525
2526                 /* execute the operator */
2527                 BMO_op_exec(em->bm, &bmop);
2528
2529                 /* finish the operator */
2530                 if (!EDBM_op_finish(em, &bmop, op, true)) {
2531                         continue;
2532                 }
2533                 EDBM_update_generic(em, false, false);
2534         }
2535
2536         MEM_freeN(objects);
2537         return OPERATOR_FINISHED;
2538 }
2539
2540 static int edbm_rotate_colors_exec(bContext *C, wmOperator *op)
2541 {
2542                 /* get the direction from RNA */
2543         const bool use_ccw = RNA_boolean_get(op->ptr, "use_ccw");
2544
2545         ViewLayer *view_layer = CTX_data_view_layer(C);
2546         uint objects_len = 0;
2547         Object **objects = BKE_view_layer_array_from_objects_in_edit_mode_unique_data(view_layer, &objects_len);
2548
2549         for (uint ob_index = 0; ob_index < objects_len; ob_index++) {
2550                 Object *ob = objects[ob_index];
2551                 BMEditMesh *em = BKE_editmesh_from_object(ob);
2552                 if (em->bm->totfacesel == 0) {
2553                         continue;
2554                 }
2555
2556                 BMOperator bmop;
2557
2558                 /* initialize the bmop using EDBM api, which does various ui error reporting and other stuff */
2559                 EDBM_op_init(em, &bmop, op, "rotate_colors faces=%hf use_ccw=%b", BM_ELEM_SELECT, use_ccw);
2560
2561                 /* execute the operator */
2562                 BMO_op_exec(em->bm, &bmop);
2563
2564                 /* finish the operator */
2565                 if (!EDBM_op_finish(em, &bmop, op, true)) {
2566                         continue;
2567                 }
2568
2569                 /* dependencies graph and notification stuff */
2570                 EDBM_update_generic(em, false, false);
2571         }
2572
2573         MEM_freeN(objects);
2574
2575         return OPERATOR_FINISHED;
2576 }
2577
2578
2579 static int edbm_reverse_colors_exec(bContext *C, wmOperator *op)
2580 {
2581         ViewLayer *view_layer = CTX_data_view_layer(C);
2582         uint objects_len = 0;
2583         Object **objects = BKE_view_layer_array_from_objects_in_edit_mode_unique_data(view_layer, &objects_len);
2584
2585         for (uint ob_index = 0; ob_index < objects_len; ob_index++) {
2586                 Object *ob = objects[ob_index];
2587                 BMEditMesh *em = BKE_editmesh_from_object(ob);
2588
2589                 if (em->bm->totfacesel == 0) {
2590                         continue;
2591                 }
2592
2593                 BMOperator bmop;
2594
2595                 /* initialize the bmop using EDBM api, which does various ui error reporting and other stuff */
2596                 EDBM_op_init(em, &bmop, op, "reverse_colors faces=%hf", BM_ELEM_SELECT);
2597
2598                 /* execute the operator */
2599                 BMO_op_exec(em->bm, &bmop);
2600
2601                 /* finish the operator */
2602                 if (!EDBM_op_finish(em, &bmop, op, true)) {
2603                         return OPERATOR_CANCELLED;
2604                 }
2605
2606                 EDBM_update_generic(em, false, false);
2607         }
2608         MEM_freeN(objects);
2609
2610         return OPERATOR_FINISHED;
2611 }
2612
2613 void MESH_OT_uvs_rotate(wmOperatorType *ot)
2614 {
2615         /* identifiers */
2616         ot->name = "Rotate UVs";
2617         ot->idname = "MESH_OT_uvs_rotate";
2618         ot->description = "Rotate UV coordinates inside faces";
2619
2620         /* api callbacks */
2621         ot->exec = edbm_rotate_uvs_exec;
2622         ot->poll = ED_operator_editmesh;
2623
2624         /* flags */
2625         ot->flag = OPTYPE_REGISTER | OPTYPE_UNDO;
2626
2627         /* props */
2628         RNA_def_boolean(ot->srna, "use_ccw", false, "Counter Clockwise", "");
2629 }
2630
2631 void MESH_OT_uvs_reverse(wmOperatorType *ot)
2632 {
2633         /* identifiers */
2634         ot->name = "Reverse UVs";
2635         ot->idname = "MESH_OT_uvs_reverse";
2636         ot->description = "Flip direction of UV coordinates inside faces";
2637
2638         /* api callbacks */
2639         ot->exec = edbm_reverse_uvs_exec;
2640         ot->poll = ED_operator_editmesh;
2641
2642         /* flags */
2643         ot->flag = OPTYPE_REGISTER | OPTYPE_UNDO;
2644
2645         /* props */
2646         //RNA_def_enum(ot->srna, "axis", axis_items, DIRECTION_CW, "Axis", "Axis to mirror UVs around");
2647 }
2648
2649 void MESH_OT_colors_rotate(wmOperatorType *ot)
2650 {
2651         /* identifiers */
2652         ot->name = "Rotate Colors";
2653         ot->idname = "MESH_OT_colors_rotate";
2654         ot->description = "Rotate vertex colors inside faces";
2655
2656         /* api callbacks */
2657         ot->exec = edbm_rotate_colors_exec;
2658         ot->poll = ED_operator_editmesh;
2659
2660         /* flags */
2661         ot->flag = OPTYPE_REGISTER | OPTYPE_UNDO;
2662
2663         /* props */
2664         RNA_def_boolean(ot->srna, "use_ccw", false, "Counter Clockwise", "");
2665 }
2666
2667 void MESH_OT_colors_reverse(wmOperatorType *ot)
2668 {
2669         /* identifiers */
2670         ot->name = "Reverse Colors";
2671         ot->idname = "MESH_OT_colors_reverse";
2672         ot->description = "Flip direction of vertex colors inside faces";
2673
2674         /* api callbacks */
2675         ot->exec = edbm_reverse_colors_exec;
2676         ot->poll = ED_operator_editmesh;
2677
2678         /* flags */
2679         ot->flag = OPTYPE_REGISTER | OPTYPE_UNDO;
2680
2681         /* props */
2682         //RNA_def_enum(ot->srna, "axis", axis_items, DIRECTION_CW, "Axis", "Axis to mirror colors around");
2683 }
2684
2685 /** \} */
2686
2687 /* -------------------------------------------------------------------- */
2688 /** \name Merge Vertices Operator
2689  * \{ */
2690
2691 enum {
2692         MESH_MERGE_LAST     = 1,
2693         MESH_MERGE_CENTER   = 3,
2694         MESH_MERGE_CURSOR   = 4,
2695         MESH_MERGE_COLLAPSE = 5,
2696         MESH_MERGE_FIRST    = 6,
2697 };
2698
2699 static bool merge_firstlast(BMEditMesh *em, const bool use_first, const bool use_uvmerge, wmOperator *wmop)
2700 {
2701         BMVert *mergevert;
2702         BMEditSelection *ese;
2703
2704         /* operator could be called directly from shortcut or python,
2705          * so do extra check for data here
2706          */
2707
2708         /* do sanity check in mergemenu in edit.c ?*/
2709         if (use_first == false) {
2710                 if (!em->bm->selected.last || ((BMEditSelection *)em->bm->selected.last)->htype != BM_VERT)
2711                         return false;
2712
2713                 ese = em->bm->selected.last;
2714                 mergevert = (BMVert *)ese->ele;
2715         }
2716         else {
2717                 if (!em->bm->selected.first || ((BMEditSelection *)em->bm->selected.first)->htype != BM_VERT)
2718                         return false;
2719
2720                 ese = em->bm->selected.first;
2721                 mergevert = (BMVert *)ese->ele;
2722         }
2723
2724         if (!BM_elem_flag_test(mergevert, BM_ELEM_SELECT))
2725                 return false;
2726
2727         if (use_uvmerge) {
2728                 if (!EDBM_op_callf(em, wmop, "pointmerge_facedata verts=%hv vert_snap=%e", BM_ELEM_SELECT, mergevert))
2729                         return false;
2730         }
2731
2732         if (!EDBM_op_callf(em, wmop, "pointmerge verts=%hv merge_co=%v", BM_ELEM_SELECT, mergevert->co))
2733                 return false;
2734
2735         return true;
2736 }
2737
2738 static bool merge_target(
2739         BMEditMesh *em, Scene *scene, View3D *v3d, Object *ob,
2740         const bool use_cursor, const bool use_uvmerge, wmOperator *wmop)
2741 {
2742         BMIter iter;
2743         BMVert *v;
2744         float co[3], cent[3] = {0.0f, 0.0f, 0.0f};
2745         const float *vco = NULL;
2746
2747         if (use_cursor) {
2748                 vco = ED_view3d_cursor3d_get(scene, v3d)->location;
2749                 copy_v3_v3(co, vco);
2750                 invert_m4_m4(ob->imat, ob->obmat);
2751                 mul_m4_v3(ob->imat, co);
2752         }
2753         else {
2754                 float fac;
2755                 int i = 0;
2756                 BM_ITER_MESH (v, &iter, em->bm, BM_VERTS_OF_MESH) {
2757                         if (!BM_elem_flag_test(v, BM_ELEM_SELECT))
2758                                 continue;
2759                         add_v3_v3(cent, v->co);
2760                         i++;
2761                 }
2762
2763                 if (!i)
2764                         return false;
2765
2766                 fac = 1.0f / (float)i;
2767                 mul_v3_fl(cent, fac);
2768                 copy_v3_v3(co, cent);
2769                 vco = co;
2770         }
2771
2772         if (!vco)
2773                 return false;
2774
2775         if (use_uvmerge) {
2776                 if (!EDBM_op_callf(em, wmop, "average_vert_facedata verts=%hv", BM_ELEM_SELECT))
2777                         return false;
2778         }
2779
2780         if (!EDBM_op_callf(em, wmop, "pointmerge verts=%hv merge_co=%v", BM_ELEM_SELECT, co))
2781                 return false;
2782
2783         return true;
2784 }
2785
2786 static int edbm_merge_exec(bContext *C, wmOperator *op)
2787 {
2788         Scene *scene = CTX_data_scene(C);
2789         View3D *v3d = CTX_wm_view3d(C);
2790         ViewLayer *view_layer = CTX_data_view_layer(C);
2791         uint objects_len = 0;
2792         Object **objects = BKE_view_layer_array_from_objects_in_edit_mode_unique_data(view_layer, &objects_len);
2793         const int type = RNA_enum_get(op->ptr, "type");
2794         const bool uvs = RNA_boolean_get(op->ptr, "uvs");
2795
2796         for (uint ob_index = 0; ob_index < objects_len; ob_index++) {
2797                 Object *obedit = objects[ob_index];
2798                 BMEditMesh *em = BKE_editmesh_from_object(obedit);
2799
2800                 if (em->bm->totvertsel == 0) {
2801                         continue;
2802                 }
2803
2804                 bool ok = false;
2805                 switch (type) {
2806                         case MESH_MERGE_CENTER:
2807                                 ok = merge_target(em, scene, v3d, obedit, false, uvs, op);
2808                                 break;
2809                         case MESH_MERGE_CURSOR:
2810                                 ok = merge_target(em, scene, v3d, obedit, true, uvs, op);
2811                                 break;
2812                         case MESH_MERGE_LAST:
2813                                 ok = merge_firstlast(em, false, uvs, op);
2814                                 break;
2815                         case MESH_MERGE_FIRST:
2816                                 ok = merge_firstlast(em, true, uvs, op);
2817                                 break;
2818                         case MESH_MERGE_COLLAPSE:
2819                                 ok = EDBM_op_callf(em, op, "collapse edges=%he uvs=%b", BM_ELEM_SELECT, uvs);
2820                                 break;
2821                         default:
2822                                 BLI_assert(0);
2823                                 break;
2824                 }
2825
2826                 if (!ok) {
2827                         continue;
2828                 }
2829
2830                 EDBM_update_generic(em, true, true);
2831
2832                 /* once collapsed, we can't have edge/face selection */
2833                 if ((em->selectmode & SCE_SELECT_VERTEX) == 0) {
2834                         EDBM_flag_disable_all(em, BM_ELEM_SELECT);
2835                 }
2836                 /* Only active object supported, see comment below. */
2837                 if (ELEM(type, MESH_MERGE_FIRST, MESH_MERGE_LAST)) {
2838                         break;
2839                 }
2840         }
2841
2842         MEM_freeN(objects);
2843
2844         return OPERATOR_FINISHED;
2845 }
2846
2847 static const EnumPropertyItem merge_type_items[] = {
2848         {MESH_MERGE_FIRST, "FIRST", 0, "At First", ""},
2849         {MESH_MERGE_LAST, "LAST", 0, "At Last", ""},
2850         {MESH_MERGE_CENTER, "CENTER", 0, "At Center", ""},
2851         {MESH_MERGE_CURSOR, "CURSOR", 0, "At Cursor", ""},
2852         {MESH_MERGE_COLLAPSE, "COLLAPSE", 0, "Collapse", ""},
2853         {0, NULL, 0, NULL, NULL}
2854 };
2855
2856 static const EnumPropertyItem *merge_type_itemf(bContext *C, PointerRNA *UNUSED(ptr),  PropertyRNA *UNUSED(prop), bool *r_free)
2857 {
2858         Object *obedit;
2859         EnumPropertyItem *item = NULL;
2860         int totitem = 0;
2861
2862         if (!C) /* needed for docs */
2863                 return merge_type_items;
2864
2865         obedit = CTX_data_edit_object(C);
2866         if (obedit && obedit->type == OB_MESH) {
2867                 BMEditMesh *em = BKE_editmesh_from_object(obedit);
2868
2869                 /* Only active object supported:
2870                  * In practice it doesn't make sense to run this operation on non-active meshes
2871                  * since selecting will activate - we could have own code-path for these but it's a hassle
2872                  * for now just apply to the active (first) object. */
2873                 if (em->selectmode & SCE_SELECT_VERTEX) {
2874                         if (em->bm->selected.first && em->bm->selected.last &&
2875                             ((BMEditSelection *)em->bm->selected.first)->htype == BM_VERT &&
2876                             ((BMEditSelection *)em->bm->selected.last)->htype == BM_VERT)
2877                         {
2878                                 RNA_enum_items_add_value(&item, &totitem, merge_type_items, MESH_MERGE_FIRST);
2879                                 RNA_enum_items_add_value(&item, &totitem, merge_type_items, MESH_MERGE_LAST);
2880                         }
2881                         else if (em->bm->selected.first && ((BMEditSelection *)em->bm->selected.first)->htype == BM_VERT) {
2882                                 RNA_enum_items_add_value(&item, &totitem, merge_type_items, MESH_MERGE_FIRST);
2883                         }
2884                         else if (em->bm->selected.last && ((BMEditSelection *)em->bm->selected.last)->htype == BM_VERT) {
2885                                 RNA_enum_items_add_value(&item, &totitem, merge_type_items, MESH_MERGE_LAST);
2886                         }
2887                 }
2888
2889                 RNA_enum_items_add_value(&item, &totitem, merge_type_items, MESH_MERGE_CENTER);
2890                 RNA_enum_items_add_value(&item, &totitem, merge_type_items, MESH_MERGE_CURSOR);
2891                 RNA_enum_items_add_value(&item, &totitem, merge_type_items, MESH_MERGE_COLLAPSE);
2892                 RNA_enum_item_end(&item, &totitem);
2893
2894                 *r_free = true;
2895
2896                 return item;
2897         }
2898
2899         return NULL;
2900 }
2901
2902 void MESH_OT_merge(wmOperatorType *ot)
2903 {
2904         /* identifiers */
2905         ot->name = "Merge";
2906         ot->description = "Merge selected vertices";
2907         ot->idname = "MESH_OT_merge";
2908
2909         /* api callbacks */
2910         ot->exec = edbm_merge_exec;
2911         ot->invoke = WM_menu_invoke;
2912         ot->poll = ED_operator_editmesh;
2913
2914         /* flags */
2915         ot->flag = OPTYPE_REGISTER | OPTYPE_UNDO;
2916
2917         /* properties */
2918         ot->prop = RNA_def_enum(ot->srna, "type", merge_type_items, MESH_MERGE_CENTER, "Type", "Merge method to use");
2919         RNA_def_enum_funcs(ot->prop, merge_type_itemf);
2920
2921         WM_operatortype_props_advanced_begin(ot);
2922
2923         RNA_def_boolean(ot->srna, "uvs", false, "UVs", "Move UVs according to merge");
2924 }
2925
2926 /** \} */
2927
2928 /* -------------------------------------------------------------------- */
2929 /** \name Remove Doubles Operator
2930  * \{ */
2931
2932 static int edbm_remove_doubles_exec(bContext *C, wmOperator *op)
2933 {
2934         const float threshold = RNA_float_get(op->ptr, "threshold");
2935         const bool use_unselected = RNA_boolean_get(op->ptr, "use_unselected");
2936         int count_multi = 0;
2937
2938         ViewLayer *view_layer = CTX_data_view_layer(C);
2939         uint objects_len = 0;
2940         Object **objects = BKE_view_layer_array_from_objects_in_edit_mode_unique_data(view_layer, &objects_len);
2941
2942         for (uint ob_index = 0; ob_index < objects_len; ob_index++) {
2943                 Object *obedit = objects[ob_index];
2944                 BMEditMesh *em = BKE_editmesh_from_object(obedit);
2945
2946                 /* Selection used as target with 'use_unselected'. */
2947                 if (em->bm->totvertsel == 0) {
2948                         continue;
2949                 }
2950
2951                 BMOperator bmop;
2952                 const int totvert_orig = em->bm->totvert;
2953
2954                 /* avoid loosing selection state (select -> tags) */
2955                 char htype_select;
2956                 if      (em->selectmode & SCE_SELECT_VERTEX) htype_select = BM_VERT;
2957                 else if (em->selectmode & SCE_SELECT_EDGE)   htype_select = BM_EDGE;
2958                 else                                         htype_select = BM_FACE;
2959
2960                 /* store selection as tags */
2961                 BM_mesh_elem_hflag_enable_test(em->bm, htype_select, BM_ELEM_TAG, true, true, BM_ELEM_SELECT);
2962
2963
2964                 if (use_unselected) {
2965                         EDBM_op_init(
2966                                 em, &bmop, op,
2967                                 "automerge verts=%hv dist=%f",
2968                                 BM_ELEM_SELECT, threshold);
2969                         BMO_op_exec(em->bm, &bmop);
2970
2971                         if (!EDBM_op_finish(em, &bmop, op, true)) {
2972                                 continue;
2973                         }
2974                 }
2975                 else {
2976                         EDBM_op_init(
2977                                 em, &bmop, op,
2978                                 "find_doubles verts=%hv dist=%f",
2979                                 BM_ELEM_SELECT, threshold);
2980
2981                         BMO_op_exec(em->bm, &bmop);
2982
2983                         if (!EDBM_op_callf(em, op, "weld_verts targetmap=%S", &bmop, "targetmap.out")) {
2984                                 BMO_op_finish(em->bm, &bmop);
2985                                 continue;
2986                         }
2987
2988                         if (!EDBM_op_finish(em, &bmop, op, true)) {
2989                                 continue;
2990                         }
2991                 }
2992
2993                 const int count = (totvert_orig - em->bm->totvert);
2994
2995                 /* restore selection from tags */
2996                 BM_mesh_elem_hflag_enable_test(em->bm, htype_select, BM_ELEM_SELECT, true, true, BM_ELEM_TAG);
2997                 EDBM_selectmode_flush(em);
2998
2999                 if (count) {
3000                         count_multi += count;
3001                         EDBM_update_generic(em, true, true);
3002                 }
3003         }
3004         MEM_freeN(objects);
3005
3006         BKE_reportf(op->reports, RPT_INFO, "Removed %d vertices", count_multi);
3007
3008         return OPERATOR_FINISHED;
3009 }
3010
3011 void MESH_OT_remove_doubles(wmOperatorType *ot)
3012 {
3013         /* identifiers */
3014         ot->name = "Remove Doubles";
3015         ot->description = "Remove duplicate vertices";
3016         ot->idname = "MESH_OT_remove_doubles";
3017
3018         /* api callbacks */
3019         ot->exec = edbm_remove_doubles_exec;
3020         ot->poll = ED_operator_editmesh;
3021
3022         /* flags */
3023         ot->flag = OPTYPE_REGISTER | OPTYPE_UNDO;
3024
3025         RNA_def_float_distance(ot->srna, "threshold", 1e-4f, 1e-6f, 50.0f, "Merge Distance",
3026                                "Minimum distance between elements to merge", 1e-5f, 10.0f);
3027         RNA_def_boolean(ot->srna, "use_unselected", false, "Unselected", "Merge selected to other unselected vertices");
3028 }
3029
3030 /** \} */
3031
3032 /* -------------------------------------------------------------------- */
3033 /** \name Shape Key Propagate Operator
3034  * \{ */
3035
3036 /* BMESH_TODO this should be properly encapsulated in a bmop.  but later.*/
3037 static bool shape_propagate(BMEditMesh *em)
3038 {
3039         BMIter iter;
3040         BMVert *eve = NULL;
3041         float *co;
3042         int totshape = CustomData_number_of_layers(&em->bm->vdata, CD_SHAPEKEY);
3043
3044         if (!CustomData_has_layer(&em->bm->vdata, CD_SHAPEKEY)) {
3045                 return false;
3046         }
3047
3048         BM_ITER_MESH (eve, &iter, em->bm, BM_VERTS_OF_MESH) {
3049                 if (!BM_elem_flag_test(eve, BM_ELEM_SELECT) || BM_elem_flag_test(eve, BM_ELEM_HIDDEN)) {
3050                         continue;
3051                 }
3052
3053                 for (int i = 0; i < totshape; i++) {
3054                         co = CustomData_bmesh_get_n(&em->bm->vdata, eve->head.data, CD_SHAPEKEY, i);
3055                         copy_v3_v3(co, eve->co);
3056                 }
3057         }
3058         return true;
3059 }
3060
3061 static int edbm_shape_propagate_to_all_exec(bContext *C, wmOperator *op)
3062 {
3063         ViewLayer *view_layer = CTX_data_view_layer(C);
3064         int tot_shapekeys = 0;
3065         int tot_selected_verts_objects = 0;
3066
3067         uint objects_len = 0;
3068         Object **objects = BKE_view_layer_array_from_objects_in_edit_mode_unique_data(view_layer, &objects_len);
3069         for (uint ob_index = 0; ob_index < objects_len; ob_index++) {
3070                 Object *obedit = objects[ob_index];
3071                 Mesh *me = obedit->data;
3072                 BMEditMesh *em = me->edit_btmesh;
3073
3074                 if (em->bm->totvertsel == 0) {
3075                         continue;
3076                 }
3077                 tot_selected_verts_objects++;
3078
3079                 if (shape_propagate(em)) {
3080                         tot_shapekeys++;
3081                 }
3082
3083                 EDBM_update_generic(em, false, false);
3084         }
3085         MEM_freeN(objects);
3086
3087         if (tot_selected_verts_objects == 0) {
3088                 BKE_report(op->reports, RPT_ERROR, "No selected vertex");
3089                 return OPERATOR_CANCELLED;
3090         }
3091         else if (tot_shapekeys == 0) {
3092                 BKE_report(
3093                         op->reports,
3094                         RPT_ERROR,
3095                         objects_len > 1 ?
3096                         "Meshes do not have shape keys" :
3097                         "Mesh does not have shape keys");
3098                 return OPERATOR_CANCELLED;
3099         }
3100
3101         return OPERATOR_FINISHED;
3102 }
3103
3104
3105 void MESH_OT_shape_propagate_to_all(wmOperatorType *ot)
3106 {
3107         /* identifiers */
3108         ot->name = "Shape Propagate";
3109         ot->description = "Apply selected vertex locations to all other shape keys";
3110         ot->idname = "MESH_OT_shape_propagate_to_all";
3111
3112         /* api callbacks */
3113         ot->exec = edbm_shape_propagate_to_all_exec;
3114         ot->poll = ED_operator_editmesh;
3115
3116         /* flags */
3117         ot->flag = OPTYPE_REGISTER | OPTYPE_UNDO;
3118 }
3119
3120 /** \} */
3121
3122 /* -------------------------------------------------------------------- */
3123 /** \name Blend from Shape Operator
3124  * \{ */
3125
3126 /* BMESH_TODO this should be properly encapsulated in a bmop.  but later.*/
3127 static int edbm_blend_from_shape_exec(bContext *C, wmOperator *op)
3128 {
3129         Object *obedit_ref = CTX_data_edit_object(C);
3130         Mesh *me_ref = obedit_ref->data;
3131         Key *key_ref = me_ref->key;
3132         KeyBlock *kb_ref = NULL;
3133         BMEditMesh *em_ref = me_ref->edit_btmesh;
3134         BMVert *eve;
3135         BMIter iter;
3136         ViewLayer *view_layer = CTX_data_view_layer(C);
3137         float co[3], *sco;
3138         int totshape_ref = 0;
3139
3140         const float blend = RNA_float_get(op->ptr, "blend");
3141         int shape_ref = RNA_enum_get(op->ptr, "shape");
3142         const bool use_add = RNA_boolean_get(op->ptr, "add");
3143
3144         /* Sanity check. */
3145         totshape_ref = CustomData_number_of_layers(&em_ref->bm->vdata, CD_SHAPEKEY);
3146
3147         if (totshape_ref == 0 || shape_ref < 0) {
3148                 BKE_report(op->reports, RPT_ERROR, "Active mesh does not have shape keys");
3149                 return OPERATOR_CANCELLED;
3150         }
3151         else if (shape_ref >= totshape_ref) {
3152                 /* This case occurs if operator was used before on object with more keys than current one. */
3153                 shape_ref = 0; /* default to basis */
3154         }
3155
3156         /* Get shape key - needed for finding reference shape (for add mode only). */
3157         if (key_ref) {
3158                 kb_ref = BLI_findlink(&key_ref->block, shape_ref);
3159         }
3160
3161         int tot_selected_verts_objects = 0;
3162         uint objects_len = 0;
3163         Object **objects = BKE_view_layer_array_from_objects_in_edit_mode_unique_data(view_layer, &objects_len);
3164         for (uint ob_index = 0; ob_index < objects_len; ob_index++) {
3165                 Object *obedit = objects[ob_index];
3166                 Mesh *me = obedit->data;
3167                 Key *key = me->key;
3168                 KeyBlock *kb = NULL;
3169                 BMEditMesh *em = me->edit_btmesh;
3170                 int shape;
3171
3172                 if (em->bm->totvertsel == 0) {
3173                         continue;
3174                 }
3175                 tot_selected_verts_objects++;
3176
3177                 if (!key) {
3178                         continue;
3179                 }
3180                 else {
3181                         kb = BKE_keyblock_find_name(key, kb_ref->name);
3182                         shape = BLI_findindex(&key->block, kb);
3183                 }
3184
3185                 if (kb) {
3186                         /* Perform blending on selected vertices. */
3187                         BM_ITER_MESH (eve, &iter, em->bm, BM_VERTS_OF_MESH) {
3188                                 if (!BM_elem_flag_test(eve, BM_ELEM_SELECT) || BM_elem_flag_test(eve, BM_ELEM_HIDDEN))
3189                                         continue;
3190
3191                                 /* Get coordinates of shapekey we're blending from. */
3192                                 sco = CustomData_bmesh_get_n(&em->bm->vdata, eve->head.data, CD_SHAPEKEY, shape);
3193                                 copy_v3_v3(co, sco);
3194
3195                                 if (use_add) {
3196                                         /* In add mode, we add relative shape key offset. */
3197                                         if (kb) {
3198                                                 const float *rco = CustomData_bmesh_get_n(&em->bm->vdata, eve->head.data, CD_SHAPEKEY, kb->relative);
3199                                                 sub_v3_v3v3(co, co, rco);
3200                                         }
3201
3202                                         madd_v3_v3fl(eve->co, co, blend);
3203                                 }
3204                                 else {
3205                                         /* In blend mode, we interpolate to the shape key. */
3206                                         interp_v3_v3v3(eve->co, eve->co, co, blend);
3207                                 }
3208                         }
3209                         EDBM_update_generic(em, true, false);
3210                 }
3211         }
3212         MEM_freeN(objects);
3213
3214         if (tot_selected_verts_objects == 0) {
3215                 BKE_report(op->reports, RPT_ERROR, "No selected vertex");
3216                 return OPERATOR_CANCELLED;
3217         }
3218
3219         return OPERATOR_FINISHED;
3220 }
3221
3222 static const EnumPropertyItem *shape_itemf(bContext *C, PointerRNA *UNUSED(ptr),  PropertyRNA *UNUSED(prop), bool *r_free)
3223 {
3224         Object *obedit = CTX_data_edit_object(C);
3225         BMEditMesh *em;
3226         EnumPropertyItem *item = NULL;
3227         int totitem = 0;
3228
3229         if ((obedit && obedit->type == OB_MESH) &&
3230             (em = BKE_editmesh_from_object(obedit)) &&
3231             CustomData_has_layer(&em->bm->vdata, CD_SHAPEKEY))
3232         {
3233                 EnumPropertyItem tmp = {0, "", 0, "", ""};
3234                 int a;
3235
3236                 for (a = 0; a < em->bm->vdata.totlayer; a++) {
3237                         if (em->bm->vdata.layers[a].type != CD_SHAPEKEY)
3238                                 continue;
3239
3240                &nb