[Bf-blender-cvs] [72b422c1e10] blender-v2.90-release: UV: support select linked with sync-select in vert/edge modes

Campbell Barton noreply at git.blender.org
Sat Aug 1 04:17:40 CEST 2020


Commit: 72b422c1e101dce18ddff5a4221665a80e58d78d
Author: Campbell Barton
Date:   Sat Aug 1 11:34:42 2020 +1000
Branches: blender-v2.90-release
https://developer.blender.org/rB72b422c1e101dce18ddff5a4221665a80e58d78d

UV: support select linked with sync-select in vert/edge modes

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

M	source/blender/editors/uvedit/uvedit_select.c

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

diff --git a/source/blender/editors/uvedit/uvedit_select.c b/source/blender/editors/uvedit/uvedit_select.c
index aff891c4023..151c881a466 100644
--- a/source/blender/editors/uvedit/uvedit_select.c
+++ b/source/blender/editors/uvedit/uvedit_select.c
@@ -1263,11 +1263,13 @@ static void uv_select_linked_multi(Scene *scene,
                                    Object **objects,
                                    const uint objects_len,
                                    UvNearestHit *hit_final,
-                                   bool extend,
+                                   const bool extend,
                                    bool deselect,
-                                   bool toggle,
-                                   bool select_faces)
+                                   const bool toggle,
+                                   const bool select_faces)
 {
+  const bool uv_sync_select = (scene->toolsettings->uv_flag & UV_SYNC_SELECTION);
+
   /* loop over objects, or just use hit_final->ob */
   for (uint ob_index = 0; ob_index < objects_len; ob_index++) {
     if (hit_final && ob_index != 0) {
@@ -1278,7 +1280,6 @@ static void uv_select_linked_multi(Scene *scene,
     BMFace *efa;
     BMLoop *l;
     BMIter iter, liter;
-    MLoopUV *luv;
     UvVertMap *vmap;
     UvMapVert *vlist, *iterv, *startv;
     int i, stacksize = 0, *stack;
@@ -1296,7 +1297,7 @@ static void uv_select_linked_multi(Scene *scene,
      *
      * Better solve this by having a delimit option for select-linked operator,
      * keeping island-select working as is. */
-    vmap = BM_uv_vert_map_create(em->bm, !select_faces, false);
+    vmap = BM_uv_vert_map_create(em->bm, !uv_sync_select, false);
 
     if (vmap == NULL) {
       continue;
@@ -1318,14 +1319,42 @@ static void uv_select_linked_multi(Scene *scene,
           }
           else {
             BM_ITER_ELEM (l, &liter, efa, BM_LOOPS_OF_FACE) {
-              luv = BM_ELEM_CD_GET_VOID_P(l, cd_loop_uv_offset);
-
-              if (luv->flag & MLOOPUV_VERTSEL) {
-                stack[stacksize] = a;
-                stacksize++;
-                flag[a] = 1;
+              if (uvedit_uv_select_test(scene, l, cd_loop_uv_offset)) {
+                bool add_to_stack = true;
+                if (uv_sync_select && !select_faces) {
+                  /* Special case, vertex/edge & sync select being enabled.
+                   *
+                   * Without this, a second linked select will 'grow' each time as each new
+                   * selection reaches the boundaries of islands that share vertices but not UV's.
+                   *
+                   * Rules applied here:
+                   * - This loops face isn't selected.
+                   * - The only other fully selected face is connected or,
+                   * - There are no connected fully selected faces UV-connected to this loop.
+                   */
+                  if (uvedit_face_select_test(scene, l->f, cd_loop_uv_offset)) {
+                    /* pass */
+                  }
+                  else {
+                    BMIter liter_other;
+                    BMLoop *l_other;
+                    BM_ITER_ELEM (l_other, &liter_other, l->v, BM_LOOPS_OF_VERT) {
+                      if ((l != l_other) &&
+                          !BM_loop_uv_share_vert_check(l, l_other, cd_loop_uv_offset) &&
+                          uvedit_face_select_test(scene, l_other->f, cd_loop_uv_offset)) {
+                        add_to_stack = false;
+                        break;
+                      }
+                    }
+                  }
+                }
 
-                break;
+                if (add_to_stack) {
+                  stack[stacksize] = a;
+                  stacksize++;
+                  flag[a] = 1;
+                  break;
+                }
               }
             }
           }
@@ -1394,10 +1423,9 @@ static void uv_select_linked_multi(Scene *scene,
         }
         else {
           BM_ITER_ELEM (l, &liter, efa, BM_LOOPS_OF_FACE) {
-            luv = BM_ELEM_CD_GET_VOID_P(l, cd_loop_uv_offset);
-
-            if (luv->flag & MLOOPUV_VERTSEL) {
+            if (uvedit_uv_select_test(scene, l, cd_loop_uv_offset)) {
               found_selected = true;
+              break;
             }
           }
 
@@ -1414,10 +1442,7 @@ static void uv_select_linked_multi(Scene *scene,
     BM_face_select_set(em->bm, efa, value); \
   } \
   else { \
-    BM_ITER_ELEM (l, &liter, efa, BM_LOOPS_OF_FACE) { \
-      luv = BM_ELEM_CD_GET_VOID_P(l, cd_loop_uv_offset); \
-      luv->flag = (value) ? (luv->flag | MLOOPUV_VERTSEL) : (luv->flag & ~MLOOPUV_VERTSEL); \
-    } \
+    uvedit_face_select_set(scene, em, efa, value, false, cd_loop_uv_offset); \
   } \
   (void)0
 
@@ -1442,6 +1467,17 @@ static void uv_select_linked_multi(Scene *scene,
     MEM_freeN(stack);
     MEM_freeN(flag);
     BM_uv_vert_map_free(vmap);
+
+    if (uv_sync_select) {
+      if (deselect) {
+        EDBM_deselect_flush(em);
+      }
+      else {
+        if (!select_faces) {
+          EDBM_selectmode_flush(em);
+        }
+      }
+    }
   }
 }
 
@@ -2263,13 +2299,6 @@ static int uv_select_linked_internal(bContext *C, wmOperator *op, const wmEvent
 
   UvNearestHit hit = UV_NEAREST_HIT_INIT;
 
-  if ((ts->uv_flag & UV_SYNC_SELECTION) && !(ts->selectmode & SCE_SELECT_FACE)) {
-    BKE_report(op->reports,
-               RPT_ERROR,
-               "Select linked only works in face select mode when sync selection is enabled");
-    return OPERATOR_CANCELLED;
-  }
-
   if (pick) {
     extend = RNA_boolean_get(op->ptr, "extend");
     deselect = RNA_boolean_get(op->ptr, "deselect");



More information about the Bf-blender-cvs mailing list