5 button mouse support from b333rt in IRC with some edits for X11.
authorCampbell Barton <ideasman42@gmail.com>
Mon, 21 Sep 2009 05:56:43 +0000 (05:56 +0000)
committerCampbell Barton <ideasman42@gmail.com>
Mon, 21 Sep 2009 05:56:43 +0000 (05:56 +0000)
Tested in X11 where its fairly confusing.
buttons 4 and 5 are used for the wheel which is well known, but it seems 6 and 7 are used for horizontal scrolling, my mouse assigns the extra 2 buttons to events 8 & 9.

So the X11 events used for buttons called 4&5 in blender are 8&9 in X11.

The mouse buttons can be re-ordered like this once xorg starts (swaps 6,7 with 8,9)
  xmodmap -e "pointer = 1 2 3 4 5 8 9 6 7"

Couldn't test Win32, Apple not supported.
If someone wants to add horizontal scrolling its quite easy.

intern/ghost/GHOST_Types.h
intern/ghost/intern/GHOST_SystemWin32.cpp
intern/ghost/intern/GHOST_SystemX11.cpp
source/blender/editors/space_outliner/outliner.c
source/blender/makesrna/intern/rna_wm.c
source/blender/windowmanager/intern/wm_event_system.c
source/blender/windowmanager/wm_event_types.h

index 73ed0bdd1faa7970f4ee0c1840810337904d99c5..31819f341a0b66ea3ca1ea0a5e829312dfda572d 100644 (file)
@@ -132,6 +132,8 @@ typedef enum {
        GHOST_kButtonMaskLeft = 0,
        GHOST_kButtonMaskMiddle,
        GHOST_kButtonMaskRight,
+       GHOST_kButtonMaskButton4,
+       GHOST_kButtonMaskButton5,
        GHOST_kButtonNumMasks
 } GHOST_TButtonMask;
 
index 8513d056795bed2cbc96eb70a2c88f5e4d0fc942..2e89be40bcbc58f6cf340ebc7863af1a8c8b805e 100644 (file)
@@ -39,7 +39,6 @@
 #endif
 
 #include "GHOST_SystemWin32.h"
-//#include <stdio.h> //for printf()
 
 // win64 doesn't define GWL_USERDATA
 #ifdef WIN32
 #define WHEEL_DELTA 120        /* Value for rolling one detent, (old convention! MS changed it) */
 #endif // WHEEL_DELTA
 
+/* 
+ * Defines for mouse buttons 4 and 5 aka xbutton1 and xbutton2.
+ * MSDN: Declared in Winuser.h, include Windows.h 
+ * This does not seem to work with MinGW so we define our own here.
+ */
+#ifndef XBUTTON1
+#define XBUTTON1 0x0001
+#endif // XBUTTON1
+#ifndef XBUTTON2
+#define XBUTTON2 0x0002
+#endif // XBUTTON2
+#ifndef WM_XBUTTONUP
+#define WM_XBUTTONUP 524
+#endif // WM_XBUTTONUP
+#ifndef WM_XBUTTONDOWN
+#define WM_XBUTTONDOWN 523
+#endif // WM_XBUTTONDOWN
 
 #include "GHOST_Debug.h"
 #include "GHOST_DisplayManagerWin32.h"
@@ -672,6 +688,14 @@ LRESULT WINAPI GHOST_SystemWin32::s_wndProc(HWND hwnd, UINT msg, WPARAM wParam,
                                        window->registerMouseClickEvent(true);
                                        event = processButtonEvent(GHOST_kEventButtonDown, window, GHOST_kButtonMaskRight);
                                        break;
+                               case WM_XBUTTONDOWN:
+                                       window->registerMouseClickEvent(true);
+                                       if ((short) HIWORD(wParam) == XBUTTON1){
+                                               event = processButtonEvent(GHOST_kEventButtonDown, window, GHOST_kButtonMaskButton4);
+                                       }else if((short) HIWORD(wParam) == XBUTTON2){
+                                               event = processButtonEvent(GHOST_kEventButtonDown, window, GHOST_kButtonMaskButton5);
+                                       }
+                                       break;
                                case WM_LBUTTONUP:
                                        window->registerMouseClickEvent(false);
                                        event = processButtonEvent(GHOST_kEventButtonUp, window, GHOST_kButtonMaskLeft);
@@ -684,6 +708,14 @@ LRESULT WINAPI GHOST_SystemWin32::s_wndProc(HWND hwnd, UINT msg, WPARAM wParam,
                                        window->registerMouseClickEvent(false);
                                        event = processButtonEvent(GHOST_kEventButtonUp, window, GHOST_kButtonMaskRight);
                                        break;
+                               case WM_XBUTTONUP:
+                                       window->registerMouseClickEvent(false);
+                                       if ((short) HIWORD(wParam) == XBUTTON1){
+                                               event = processButtonEvent(GHOST_kEventButtonUp, window, GHOST_kButtonMaskButton4);
+                                       }else if((short) HIWORD(wParam) == XBUTTON2){
+                                               event = processButtonEvent(GHOST_kEventButtonUp, window, GHOST_kButtonMaskButton5);
+                                       }
+                                       break;
                                case WM_MOUSEMOVE:
                                        event = processCursorEvent(GHOST_kEventCursorMove, window);
                                        break;
index 9f6f3b4d5b018dd18abcd518d37d4037971d3eac..cdbdce9c2ca7647ad90db872468532bd7c44c0da 100644 (file)
@@ -444,10 +444,15 @@ GHOST_SystemX11::processEvent(XEvent *xe)
 
                        XButtonEvent & xbe = xe->xbutton;
                        GHOST_TButtonMask gbmask = GHOST_kButtonMaskLeft;
-
                        switch (xbe.button) {
                                case Button1 : gbmask = GHOST_kButtonMaskLeft; break;
                                case Button3 : gbmask = GHOST_kButtonMaskRight; break;
+                               /* It seems events 6 and 7 are for horizontal scrolling.
+                                * you can re-order button mapping like this... (swaps 6,7 with 8,9)
+                                *   xmodmap -e "pointer = 1 2 3 4 5 8 9 6 7" 
+                                */
+                               case 8 : gbmask = GHOST_kButtonMaskButton4; break; /* Button4 is the wheel */
+                               case 9 : gbmask = GHOST_kButtonMaskButton5; break; /* Button5 is a wheel too */
                                default:
                                case Button2 : gbmask = GHOST_kButtonMaskMiddle; break;
                        }
index a3b47d505fdff4a7590cf2f45ce844145a929294..a1fdbab9ccc329d0a2f6fb7b687b4caae99e4c55 100644 (file)
@@ -5049,6 +5049,8 @@ static char *keymap_mouse_menu(void)
        str += sprintf(str, formatstr, "Left Mouse", LEFTMOUSE);
        str += sprintf(str, formatstr, "Middle Mouse", MIDDLEMOUSE);
        str += sprintf(str, formatstr, "Right Mouse", RIGHTMOUSE);
+       str += sprintf(str, formatstr, "Button4 Mouse ", BUTTON4MOUSE);
+       str += sprintf(str, formatstr, "Button5 Mouse ", BUTTON5MOUSE);
        str += sprintf(str, formatstr, "Action Mouse", ACTIONMOUSE);
        str += sprintf(str, formatstr, "Select Mouse", SELECTMOUSE);
        str += sprintf(str, formatstr, "Mouse Move", MOUSEMOVE);
@@ -5071,6 +5073,8 @@ static char *keymap_tweak_menu(void)
        str += sprintf(str, formatstr, "Left Mouse", EVT_TWEAK_L);
        str += sprintf(str, formatstr, "Middle Mouse", EVT_TWEAK_M);
        str += sprintf(str, formatstr, "Right Mouse", EVT_TWEAK_R);
+       str += sprintf(str, formatstr, "Button4 Mouse ", BUTTON4MOUSE);
+       str += sprintf(str, formatstr, "Button5 Mouse ", BUTTON5MOUSE);
        str += sprintf(str, formatstr, "Action Mouse", EVT_TWEAK_A);
        str += sprintf(str, formatstr, "Select Mouse", EVT_TWEAK_S);
        
index fff51ad8ade9b6c27fe13c08dfe28a3552e24af2..0dd9e3aed421cfb35122c219a0caad4522f0cf43 100644 (file)
@@ -46,6 +46,8 @@ EnumPropertyItem event_type_items[] = {
        {LEFTMOUSE, "LEFTMOUSE", 0, "Left Mouse", ""},
        {MIDDLEMOUSE, "MIDDLEMOUSE", 0, "Middle Mouse", ""},
        {RIGHTMOUSE, "RIGHTMOUSE", 0, "Right Mouse", ""},
+       {BUTTON4MOUSE, "BUTTON4MOUSE", 0, "Button4 Mouse", ""},
+       {BUTTON5MOUSE, "BUTTON5MOUSE", 0, "Button5 Mouse", ""},
        {ACTIONMOUSE, "ACTIONMOUSE", 0, "Action Mouse", ""},
        {SELECTMOUSE, "SELECTMOUSE", 0, "Select Mouse", ""},
 
index 40026d27bac7f4b13e7d4da08fd1f5c67045640d..ebb7adc3cd51ed869f237223d81df6e6aa15ea72 100644 (file)
@@ -1579,6 +1579,10 @@ void wm_event_add_ghostevent(wmWindow *win, int type, void *customdata)
                                event.type= LEFTMOUSE;
                        else if (bd->button == GHOST_kButtonMaskRight)
                                event.type= RIGHTMOUSE;
+                       else if (bd->button == GHOST_kButtonMaskButton4)
+                               event.type= BUTTON4MOUSE;
+                       else if (bd->button == GHOST_kButtonMaskButton5)
+                               event.type= BUTTON5MOUSE;
                        else
                                event.type= MIDDLEMOUSE;
                        
index b331e036b9e18302ffa73b243fe24bce5ae705a4..898c6358f3a561e48c73890e358e472399681732 100644 (file)
@@ -56,6 +56,9 @@
                /* only use if you want user option switch possible */
 #define ACTIONMOUSE            0x005
 #define SELECTMOUSE            0x006
+/* Extra mouse buttons */
+#define BUTTON4MOUSE   0x007  
+#define BUTTON5MOUSE   0x008
                /* defaults from ghost */
 #define WHEELUPMOUSE   0x00a   
 #define WHEELDOWNMOUSE 0x00b