Fix IC-keymap doesn't allow MMB to run the active tool
authorCampbell Barton <ideasman42@gmail.com>
Fri, 20 Dec 2019 00:08:41 +0000 (11:08 +1100)
committerCampbell Barton <ideasman42@gmail.com>
Fri, 20 Dec 2019 00:09:55 +0000 (11:09 +1100)
Now the keymap can be configured so both the fallback and active
tool can be activated at once - when configured not to conflict.

source/blender/editors/screen/area.c
source/blender/windowmanager/WM_api.h
source/blender/windowmanager/intern/wm_event_system.c

index e3070903ccccd8fa712d4b9d51d118d8de31a393..98bee1560900ef39f1582305ac4a28c3b4fa000b 100644 (file)
@@ -1595,6 +1595,8 @@ static void ed_default_handlers(
     }
   }
   if (flag & ED_KEYMAP_TOOL) {
+    WM_event_add_keymap_handler_dynamic(
+        &ar->handlers, WM_event_get_keymap_from_toolsystem_fallback, sa);
     WM_event_add_keymap_handler_dynamic(&ar->handlers, WM_event_get_keymap_from_toolsystem, sa);
   }
   if (flag & ED_KEYMAP_VIEW2D) {
index 72ccbb0fb55e9b7662a058c94f3b32f59c60b280..d24157a22a65d831c2e9c0c7035fe5259eee99b3 100644 (file)
@@ -228,6 +228,8 @@ struct wmEventHandler_Keymap *WM_event_add_keymap_handler_priority(ListBase *han
 typedef struct wmKeyMap *(wmEventHandler_KeymapDynamicFn)(
     wmWindowManager *wm, struct wmEventHandler_Keymap *handler)ATTR_WARN_UNUSED_RESULT;
 
+struct wmKeyMap *WM_event_get_keymap_from_toolsystem_fallback(
+    struct wmWindowManager *wm, struct wmEventHandler_Keymap *handler);
 struct wmKeyMap *WM_event_get_keymap_from_toolsystem(struct wmWindowManager *wm,
                                                      struct wmEventHandler_Keymap *handler);
 
index c1b56c0b9aef40fc6074a09f2d8557968c6de734..77d59dd3a8f92e36d639f808aa9c7ccda4fe3876 100644 (file)
@@ -3736,44 +3736,82 @@ wmEventHandler_Keymap *WM_event_add_keymap_handler(ListBase *handlers, wmKeyMap
   return handler;
 }
 
-/** Follow #wmEventHandler_KeymapDynamicFn signature. */
-wmKeyMap *WM_event_get_keymap_from_toolsystem(wmWindowManager *wm, wmEventHandler_Keymap *handler)
+/**
+ * Implements fallback tool when enabled by:
+ * #SCE_WORKSPACE_TOOL_FALLBACK, #WM_GIZMOGROUPTYPE_TOOL_FALLBACK_KEYMAP.
+ *
+ * This runs before #WM_event_get_keymap_from_toolsystem,
+ * allowing both the fallback-tool and active-tool to be activated
+ * providing the key-map is configured so the keys don't conflict.
+ * For example one mouse button can run the active-tool, another button for the fallback-tool.
+ * See T72567.
+ *
+ * Follow #wmEventHandler_KeymapDynamicFn signature.
+ */
+wmKeyMap *WM_event_get_keymap_from_toolsystem_fallback(wmWindowManager *wm,
+                                                       wmEventHandler_Keymap *handler)
 {
+  if (!USER_EXPERIMENTAL_TEST(&U, use_tool_fallback)) {
+    return NULL;
+  }
+
   ScrArea *sa = handler->dynamic.user_data;
   handler->keymap_tool = NULL;
   bToolRef_Runtime *tref_rt = sa->runtime.tool ? sa->runtime.tool->runtime : NULL;
-  if (tref_rt && (tref_rt->keymap[0] || tref_rt->keymap_fallback[0])) {
-    const char *keymap_id = tref_rt->keymap;
+  if (tref_rt && tref_rt->keymap_fallback[0]) {
+    const char *keymap_id = NULL;
 
     /* Support for the gizmo owning the tool keymap. */
-    if (USER_EXPERIMENTAL_TEST(&U, use_tool_fallback)) {
-      if (tref_rt->gizmo_group[0] != '\0' && tref_rt->keymap_fallback[0] != '\n') {
-        wmGizmoMap *gzmap = NULL;
-        wmGizmoGroup *gzgroup = NULL;
-        for (ARegion *ar = sa->regionbase.first; ar; ar = ar->next) {
-          if (ar->gizmo_map != NULL) {
-            gzmap = ar->gizmo_map;
-            gzgroup = WM_gizmomap_group_find(gzmap, tref_rt->gizmo_group);
-            if (gzgroup != NULL) {
-              break;
-            }
+    if (tref_rt->gizmo_group[0] != '\0' && tref_rt->keymap_fallback[0] != '\n') {
+      wmGizmoMap *gzmap = NULL;
+      wmGizmoGroup *gzgroup = NULL;
+      for (ARegion *ar = sa->regionbase.first; ar; ar = ar->next) {
+        if (ar->gizmo_map != NULL) {
+          gzmap = ar->gizmo_map;
+          gzgroup = WM_gizmomap_group_find(gzmap, tref_rt->gizmo_group);
+          if (gzgroup != NULL) {
+            break;
           }
         }
-        if (gzgroup != NULL) {
-          if (gzgroup->type->flag & WM_GIZMOGROUPTYPE_TOOL_FALLBACK_KEYMAP) {
-            /* If all are hidden, don't override. */
-            if (gzgroup->use_fallback_keymap) {
-              wmGizmo *highlight = wm_gizmomap_highlight_get(gzmap);
-              if (highlight == NULL) {
-                keymap_id = tref_rt->keymap_fallback;
-              }
+      }
+      if (gzgroup != NULL) {
+        if (gzgroup->type->flag & WM_GIZMOGROUPTYPE_TOOL_FALLBACK_KEYMAP) {
+          /* If all are hidden, don't override. */
+          if (gzgroup->use_fallback_keymap) {
+            wmGizmo *highlight = wm_gizmomap_highlight_get(gzmap);
+            if (highlight == NULL) {
+              keymap_id = tref_rt->keymap_fallback;
             }
           }
         }
       }
     }
 
-    if (keymap_id[0]) {
+    if (keymap_id && keymap_id[0]) {
+      wmKeyMap *km = WM_keymap_list_find_spaceid_or_empty(
+          &wm->userconf->keymaps, keymap_id, sa->spacetype, RGN_TYPE_WINDOW);
+      /* We shouldn't use keymaps from unrelated spaces. */
+      if (km != NULL) {
+        handler->keymap_tool = sa->runtime.tool;
+        return km;
+      }
+      else {
+        printf(
+            "Keymap: '%s' not found for tool '%s'\n", tref_rt->keymap, sa->runtime.tool->idname);
+      }
+    }
+  }
+  return NULL;
+}
+
+wmKeyMap *WM_event_get_keymap_from_toolsystem(wmWindowManager *wm, wmEventHandler_Keymap *handler)
+{
+  ScrArea *sa = handler->dynamic.user_data;
+  handler->keymap_tool = NULL;
+  bToolRef_Runtime *tref_rt = sa->runtime.tool ? sa->runtime.tool->runtime : NULL;
+  if (tref_rt && tref_rt->keymap[0]) {
+    const char *keymap_id = tref_rt->keymap;
+    {
       wmKeyMap *km = WM_keymap_list_find_spaceid_or_empty(
           &wm->userconf->keymaps, keymap_id, sa->spacetype, RGN_TYPE_WINDOW);
       /* We shouldn't use keymaps from unrelated spaces. */