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

git.blender.org/blender.git - Unnamed repository; edit this file 'description' to name the repository.
summaryrefslogtreecommitdiff
diff options
context:
space:
mode:
authorGermano Cavalcante <mano-wii>2021-11-17 03:05:30 +0300
committerGermano Cavalcante <germano.costa@ig.com.br>2021-11-18 19:14:18 +0300
commit1d1855e95f916685fed970904fc37701a4a0e031 (patch)
treea62ec25eb008f5b5b1d83bc2bc523ee1c8b3885f /source/blender/windowmanager
parentcb3ba68ec4470a170905a2dc9ea64b8fa1f8ace3 (diff)
Allow navigating while transforming
This feature has been desired for some time: - https://rightclickselect.com/p/ui/Tqbbbc/allow-navigating-while-transforming (See comments); - D1583; - T37427; In short, blocking navigation during transform limits the user to move the object only to visible areas within the screen and hinders the allocation of objects within closed meshes. The node editor is also impaired because some nodes are far between them and the connectors are too small. The only disadvantage of this patch (as I see it) is the conflict with the existing key map: MIDDLEMOUSE: - enable axis constrain in 3D view; WHEELDOWNMOUSE, WHEELUPMOUSE, PAGEUPKEY, PAGEDOWNKEY: - change the threshold of the proportional edit; So the patch solution was to change these keymaps: - MIDDLEMOUSE to Alt+MIDDLEMOUSE; - WHEELDOWNMOUSE, WHEELUPMOUSE, PAGEUPKEY, PAGEDOWNKEY to Alt+(corresponding key); When you use this new keymap for the first time in the proportional edit, it may seem strange due to the custom of using it (both in View2D and View3D). But quickly the user gets used to it. Alternatively we can add an option to the user preferences ([] Allow navigating while transforming). (I'm not much fan of this option). The patch was done on branch2.8. But maybe it's a good idea to apply it to 2.79 Differential Revision: https://developer.blender.org/D2624
Diffstat (limited to 'source/blender/windowmanager')
-rw-r--r--source/blender/windowmanager/WM_api.h3
-rw-r--r--source/blender/windowmanager/intern/wm_event_system.c2
-rw-r--r--source/blender/windowmanager/intern/wm_operator_utils.c101
-rw-r--r--source/blender/windowmanager/wm_event_system.h1
4 files changed, 106 insertions, 1 deletions
diff --git a/source/blender/windowmanager/WM_api.h b/source/blender/windowmanager/WM_api.h
index 8d25ece3753..35bd5ef4e3f 100644
--- a/source/blender/windowmanager/WM_api.h
+++ b/source/blender/windowmanager/WM_api.h
@@ -640,6 +640,9 @@ char *WM_operatortype_description_or_name(struct bContext *C,
/* wm_operator_utils.c */
void WM_operator_type_modal_from_exec_for_object_edit_coords(struct wmOperatorType *ot);
+bool WM_operator_do_navigation(struct bContext *C,
+ struct wmOperator *op,
+ const struct wmEvent *event);
/* wm_uilist_type.c */
void WM_uilisttype_init(void);
diff --git a/source/blender/windowmanager/intern/wm_event_system.c b/source/blender/windowmanager/intern/wm_event_system.c
index f51c8c48c48..f08c23c6543 100644
--- a/source/blender/windowmanager/intern/wm_event_system.c
+++ b/source/blender/windowmanager/intern/wm_event_system.c
@@ -2003,7 +2003,7 @@ void WM_event_remove_handlers(bContext *C, ListBase *handlers)
}
}
-static bool wm_eventmatch(const wmEvent *winevent, const wmKeyMapItem *kmi)
+bool wm_eventmatch(const wmEvent *winevent, const wmKeyMapItem *kmi)
{
if (kmi->flag & KMI_INACTIVE) {
return false;
diff --git a/source/blender/windowmanager/intern/wm_operator_utils.c b/source/blender/windowmanager/intern/wm_operator_utils.c
index 85a0a28de79..4f4259408d8 100644
--- a/source/blender/windowmanager/intern/wm_operator_utils.c
+++ b/source/blender/windowmanager/intern/wm_operator_utils.c
@@ -21,7 +21,9 @@
*/
#include <math.h>
+#include <string.h>
+#include "BLI_listbase.h"
#include "BLI_string.h"
#include "BLI_utildefines.h"
@@ -35,6 +37,8 @@
#include "WM_api.h" /* Own include. */
#include "WM_types.h"
+#include "wm_event_system.h"
+
#include "MEM_guardedalloc.h"
#include "ED_object.h"
@@ -358,4 +362,101 @@ void WM_operator_type_modal_from_exec_for_object_edit_coords(wmOperatorType *ot)
RNA_def_property_flag(prop, PROP_HIDDEN | PROP_SKIP_SAVE);
}
+bool WM_operator_do_navigation(bContext *C, wmOperator *op, const wmEvent *event)
+{
+ const char *op_names[] = {
+ /* 3D View. */
+ "VIEW3D_OT_zoom",
+ "VIEW3D_OT_rotate",
+ "VIEW3D_OT_move",
+ "VIEW3D_OT_view_pan",
+ "VIEW3D_OT_dolly",
+ "VIEW3D_OT_view_orbit",
+ "VIEW3D_OT_view_roll",
+#ifdef WITH_INPUT_NDOF
+ "VIEW3D_OT_ndof_orbit_zoom",
+ "VIEW3D_OT_ndof_orbit",
+ "VIEW3D_OT_ndof_pan",
+ "VIEW3D_OT_ndof_all",
+#endif
+ /* Image. */
+ "IMAGE_OT_view_pan",
+ "IMAGE_OT_view_zoom_in",
+ "IMAGE_OT_view_zoom_out",
+#ifdef WITH_INPUT_NDOF
+ "IMAGE_OT_view_ndof",
+#endif
+ /* View2D. */
+ "VIEW2D_OT_pan",
+ "VIEW2D_OT_zoom_in",
+ "VIEW2D_OT_zoom_out",
+#ifdef WITH_INPUT_NDOF
+ "VIEW2D_OT_ndof",
+#endif
+ };
+
+ static struct {
+ wmKeyMapItem *kmi;
+ wmOperatorType *ot;
+ } kmi_ot[70];
+ static int kmi_ot_len;
+
+ /* Lazy initialization (avoids having to allocating a context). */
+ static wmOperatorType *ot_last = NULL;
+ static char spacetype_last = SPACE_EMPTY;
+ SpaceLink *sl = CTX_wm_space_data(C);
+ if ((ot_last != op->type) || (spacetype_last != sl->spacetype)) {
+ ot_last = op->type;
+ spacetype_last = sl->spacetype;
+
+ wmWindowManager *wm = CTX_wm_manager(C);
+ wmKeyMap *km;
+ if (sl->spacetype == SPACE_VIEW3D) {
+ km = WM_keymap_find_all(wm, "3D View", SPACE_VIEW3D, 0);
+ }
+ else if (sl->spacetype == SPACE_IMAGE) {
+ km = WM_keymap_find_all(wm, "Image", SPACE_IMAGE, 0);
+ }
+ else {
+ km = WM_keymap_find_all(wm, "View2D", 0, 0);
+ }
+
+ kmi_ot_len = 0;
+ LISTBASE_FOREACH (wmKeyMapItem *, kmi, &km->items) {
+ if (!(STRPREFIX(kmi->idname, "VIEW") || STRPREFIX(kmi->idname, "IMAGE"))) {
+ continue;
+ }
+ if (kmi->flag & KMI_INACTIVE) {
+ continue;
+ }
+ for (int i = 0; i < ARRAY_SIZE(op_names); i++) {
+ if (STREQ(kmi->idname, op_names[i])) {
+ kmi_ot[kmi_ot_len].kmi = kmi;
+ kmi_ot[kmi_ot_len].ot = WM_operatortype_find(op_names[i], true);
+ kmi_ot_len++;
+ break;
+ }
+ }
+ if (kmi_ot_len == ARRAY_SIZE(kmi_ot)) {
+ BLI_assert(false);
+ break;
+ }
+ }
+ }
+
+ if (event->type == EVT_MODAL_MAP) {
+ wmWindow *win = CTX_wm_window(C);
+ event = win->eventstate;
+ }
+
+ for (int i = 0; i < kmi_ot_len; i++) {
+ if (wm_eventmatch(event, kmi_ot[i].kmi)) {
+ return WM_operator_name_call_ptr(
+ C, kmi_ot[i].ot, WM_OP_INVOKE_DEFAULT, kmi_ot[i].kmi->ptr) != OPERATOR_CANCELLED;
+ }
+ }
+
+ return false;
+}
+
/** \} */
diff --git a/source/blender/windowmanager/wm_event_system.h b/source/blender/windowmanager/wm_event_system.h
index 9b0f128d071..c90a808c65e 100644
--- a/source/blender/windowmanager/wm_event_system.h
+++ b/source/blender/windowmanager/wm_event_system.h
@@ -147,6 +147,7 @@ typedef struct wmEventHandler_Dropbox {
void wm_event_free_all(wmWindow *win);
void wm_event_free(wmEvent *event);
void wm_event_free_handler(wmEventHandler *handler);
+bool wm_eventmatch(const wmEvent *winevent, const wmKeyMapItem *kmi);
/* goes over entire hierarchy: events -> window -> screen -> area -> region */
void wm_event_do_handlers(bContext *C);