Patch for GLUT on Mac OS X for horizontal scrolling and command key modifier

Alec Jacobson

October 24, 2013

weblog/

I recently found out about a patch for the GLUT framework on Mac OS X to provide support for mouse wheel scrolling. This is great, because I was really getting tired of the X11 windows that freeGLUT uses.

I followed these instructions for building from source: grab the source from Apple and apply the 3 patches.

Unfortunately I still got compilation errors on Mac OS X 10.7.5 with Xcode 4.

Type 'id <NSMenuItem>' does not conform to the 'NSCopying' protocol

I fixed this, I changed the line in GLUTApplication.m that looks like:

- (BOOL)validateMenuItem:(id <NSMenuItem>)menuItem

to

- (BOOL)validateMenuItem:(NSMenuItem *)menuItem

Now it compiles. These patches only add support for vertical scrolling. To add horizontal scrolling I changed the scrollWheel function in GLUTView.m to this:

- (void)scrollWheel: (NSEvent *)theEvent
{
   if(_mouseFunc) {
      NSPoint location = [self convertMouseLocationToBacking: [theEvent locationInWindow]];

      float deltaY = [theEvent deltaY];
      float deltaX = [theEvent deltaX];
      int buttonID = GLUT_WHEEL_UP;
      if(deltaY < 0) {
         deltaY = -deltaY;
         buttonID = GLUT_WHEEL_DOWN;
      }else if(deltaY > 0)
      {
         buttonID = GLUT_WHEEL_UP;
      }else if(deltaX < 0)
      {
         deltaY = -deltaX;
         buttonID = GLUT_WHEEL_RIGHT;
      }else if(deltaX > 0)
      {
         deltaY = deltaX;
         buttonID = GLUT_WHEEL_LEFT;
      }

      int x = rint(location.x);
      int y = rint(location.y);

      __glutSetWindow(self);
      int i;
      for(i = 0; i < deltaY; i++) {
//       (*_mouseFunc)(buttonID, GLUT_DOWN, x, y);
         (*_mouseFunc)(buttonID, GLUT_UP, x, y);
      }
   }
}

and add the following definitions in glut.h:

#define GLUT_WHEEL_LEFT 5
#define GLUT_WHEEL_RIGHT 6

While I was at it, I also added support for catching the command (aka apple, aka ⌘) key. To do this I add the following lines to glutGetModifiers in macx_modifier.m:

   if(__glutModifierMask & NSCommandKeyMask)
      modifiers |= GLUT_ACTIVE_COMMAND;

and again added a respective definition in glut.h:

#define GLUT_ACTIVE_COMMAND             8

Now I compile and replace the GLUT.framework directory in /System/Library/Frameworks/ and I'm reading to go!

Download xcodeproject of patched glut

Update: On 10.9 OS X Mavericks, I'm getting complaints from Xcode that garbage collection is no longer supported and that I should switch to ARC. I chose "Not now", but then got a compile error complaining:

error: garbage collection is no longer supported

I fixed this, following this advice, by removing lines like

                           GCC_ENABLE_OBJC_GC = supported;

from GLUT_External.xcodeproj/project.pbxproj. I've updated the zipped project appropriately.

Update: On 10.10 OS X Yosemite my hack for getting modifier keys during mouse move and scroll events with Carbon "expired". Rather than figure out how to continue using Carbon, I've patched Glut again to reveal modifier flags during mouse move and mouse scroll events. This means that you can call glutGetModifiers during your glutPassiveMotionFunc, glutMotionFunc and when glutMouseFunc fires on a scroll event. I've updated the zipped project by appropriately enclosing these function calls between:

__glutModifierMask = [theEvent modifierFlags];
... // call func
__glutModifierMask = ~0;

**Update: ** Based on another patch I've updated mine to enable easy access to the core profile.

**Update: ** I've basically been tracking my changes via a .zip file hosted on this blog. That's not very safe. Now, I've uploaded all of the code to a github repo. You can still download everything as a zip or just clone the repo.