home *** CD-ROM | disk | FTP | other *** search
/ Big Green CD 8 / BGCD_8_Dev.iso / YellowBox / Kits / MiscTableScroll-138.1 / Palettes / MiscTableScroll / Framework / MiscTableScrollKB.M < prev    next >
Encoding:
Text File  |  1998-03-31  |  10.7 KB  |  343 lines

  1. //=============================================================================
  2. //
  3. //    Copyright (C) 1996-1997 by Paul S. McCarthy and Eric Sunshine.
  4. //        Written by Paul S. McCarthy and Eric Sunshine.
  5. //                All Rights Reserved.
  6. //
  7. //    This notice may not be removed from this source code.
  8. //
  9. //    This object is included in the MiscKit by permission from the authors
  10. //    and its use is governed by the MiscKit license, found in the file
  11. //    "License.rtf" in the MiscKit distribution.  Please refer to that file
  12. //    for a list of all applicable permissions and restrictions.
  13. //    
  14. //=============================================================================
  15. //-----------------------------------------------------------------------------
  16. // MiscTableScrollKB.M
  17. //
  18. //    Keyboard event handling for MiscTableScroll.
  19. //
  20. //-----------------------------------------------------------------------------
  21. //-----------------------------------------------------------------------------
  22. // $Id: MiscTableScrollKB.M,v 1.7 97/06/18 10:50:46 sunshine Exp $
  23. // $Log:    MiscTableScrollKB.M,v $
  24. //  Revision 1.7  97/06/18  10:50:46  sunshine
  25. //  v125.9: Worked around Objective-C++ compiler crash in OPENSTEP 4.2 for NT
  26. //  when sending message to 'super' from within a category.
  27. //  
  28. //  Revision 1.6  97/04/15  09:08:47  sunshine
  29. //  v0.125.8: Added "MiscTableScroll/" prefix to #import to facilitate new
  30. //  framework organization.
  31. //  
  32. //  Revision 1.5  97/02/09  16:26:47  sunshine
  33. //  v112.1: Now disables flushWindow during methods which scroll and change the
  34. //  keyboard cursor position so that the operations occur in a visually atomic
  35. //  fashion.  MiscTableView's moveFocusBy: --> moveCursorBy:.
  36. //-----------------------------------------------------------------------------
  37. #import <MiscTableScroll/MiscTableScroll.h>
  38. #import "MiscTableView.h"
  39.  
  40. enum KB_Action
  41.     {
  42.     ACT_IGNORE,
  43.     ACT_SELECT,
  44.     ACT_PERFORM,
  45.     ACT_LEFT,
  46.     ACT_RIGHT,
  47.     ACT_UP,
  48.     ACT_DOWN,
  49.     ACT_PAGE_LEFT,
  50.     ACT_PAGE_RIGHT,
  51.     ACT_PAGE_UP,
  52.     ACT_PAGE_DOWN,
  53.     ACT_LEFT_EDGE,
  54.     ACT_RIGHT_EDGE,
  55.     ACT_TOP_EDGE,
  56.     ACT_BOT_EDGE,
  57.  
  58.     ACT_NUM_ACTIONS
  59.     };
  60.  
  61. enum
  62.     {
  63.     K_RETURN        = '\r',
  64.     K_SPACE        = ' ' ,
  65.     K_LEFT        = NSLeftArrowFunctionKey,
  66.     K_UP        = NSUpArrowFunctionKey,
  67.     K_RIGHT        = NSRightArrowFunctionKey,
  68.     K_DOWN        = NSDownArrowFunctionKey,
  69.     K_KP_LEFT        = '4',
  70.     K_KP_UP        = '8',
  71.     K_KP_RIGHT        = '6',
  72.     K_KP_DOWN        = '2',
  73.     K_KP_PAGE_UP    = '9',
  74.     K_KP_PAGE_DOWN    = '3',
  75.     K_KP_HOME        = '7',
  76.     K_KP_END        = '1',
  77.     K_KP_INSERT        = '0',
  78.     K_KP_ENTER        = 0x03,
  79.     K_PAGE_UP        = NSPageUpFunctionKey,
  80.     K_PAGE_DOWN        = NSPageDownFunctionKey,
  81.     K_HOME        = NSHomeFunctionKey,
  82.     K_END        = NSEndFunctionKey,
  83.     };
  84.  
  85.  
  86. //=============================================================================
  87. // IMPLEMENTATION
  88. //=============================================================================
  89. @implementation MiscTableScroll(Keyboard)
  90.  
  91. //-----------------------------------------------------------------------------
  92. // - keyboardSelect:
  93. //-----------------------------------------------------------------------------
  94. - (void)keyboardSelect:(NSEvent*)p 
  95.     {
  96.     [tableView keyboardSelect:p];
  97.     [self clearSlotSelection:MISC_OTHER_BORDER([tableView trackingBy])];
  98.     [self selectionChanged];
  99.     [self sendActionIfEnabled];
  100.     }
  101.  
  102.  
  103. //-----------------------------------------------------------------------------
  104. // goFirstSlot:
  105. //-----------------------------------------------------------------------------
  106. - (void)goFirstSlot:(MiscBorderType)b
  107.     {
  108.     if ([self numberOfSlots:b] > 0)
  109.     {
  110.     int const s = [self border:b slotAtPosition:0];
  111.     NSWindow* const w = [self window];
  112.     [w disableFlushWindow];
  113.     [self border:b setCursorSlot:s];
  114.     [self border:b setFirstVisibleSlot:s];
  115.     [w enableFlushWindow];
  116.     [w flushWindow];
  117.     }
  118.     }
  119.  
  120.  
  121. //-----------------------------------------------------------------------------
  122. // goLastSlot
  123. //-----------------------------------------------------------------------------
  124. - (void)goLastSlot:(MiscBorderType)b
  125.     {
  126.     int const n = [self numberOfSlots:b];
  127.     if (n > 0)
  128.     {
  129.     int s = [self border:b slotAtPosition:(n - 1)];
  130.     NSWindow* const w = [self window];
  131.     [w disableFlushWindow];
  132.     [self border:b setCursorSlot:s];
  133.     [self border:b setLastVisibleSlot:s];
  134.     [w enableFlushWindow];
  135.     [w flushWindow];
  136.     }
  137.     }
  138.  
  139.  
  140. //-----------------------------------------------------------------------------
  141. // goPrevPage:
  142. //-----------------------------------------------------------------------------
  143. - (void)goPrevPage:(MiscBorderType)b
  144.     {
  145.     if ([self numberOfSlots:b] > 0)
  146.     {
  147.     int sFirst = [self firstVisibleSlot:b];
  148.     int const sLast  = [self lastVisibleSlot:b];
  149.     int const v = [self border:b slotPosition:sFirst];
  150.     if (sFirst == sLast && v > 0)
  151.         sFirst = [self border:b slotAtPosition:(v - 1)];
  152.     NSWindow* const w = [self window];
  153.     [w disableFlushWindow];
  154.     [self border:b setLastVisibleSlot:sFirst];
  155.     if (b == [self trackingBy])
  156.         [self border:b setCursorSlot:[self firstVisibleSlot:b]];
  157.     [w enableFlushWindow];
  158.     [w flushWindow];
  159.     }
  160.     }
  161.  
  162.  
  163. //-----------------------------------------------------------------------------
  164. // goNextPage:
  165. //-----------------------------------------------------------------------------
  166. - (void)goNextPage:(MiscBorderType)b
  167.     {
  168.     int const lim = [self numberOfSlots:b];
  169.     if (lim > 0)
  170.     {
  171.     int const sFirst = [self firstVisibleSlot:b];
  172.     int sLast = [self lastVisibleSlot:b];
  173.     int const v = [self border:b slotPosition:sLast];
  174.     if (sFirst == sLast && v < lim - 1)
  175.         sLast = [self border:b slotAtPosition:(v + 1)];
  176.     NSWindow* const w = [self window];
  177.     [w disableFlushWindow];
  178.     [self border:b setFirstVisibleSlot:sLast];
  179.     if (b == [self trackingBy])
  180.         [self border:b setCursorSlot:[self lastVisibleSlot:b]];
  181.     [w enableFlushWindow];
  182.     [w flushWindow];
  183.     }
  184.     }
  185.  
  186.  
  187. //-----------------------------------------------------------------------------
  188. // - classifyFunctionKey:
  189. //-----------------------------------------------------------------------------
  190. - (KB_Action)classifyFunctionKey:(NSEvent*)p
  191.     {
  192.     KB_Action deed = ACT_IGNORE;
  193.     switch ([[p charactersIgnoringModifiers] characterAtIndex:0])
  194.     {
  195.     case K_LEFT:        deed = ACT_LEFT;    break;
  196.     case K_RIGHT:        deed = ACT_RIGHT;    break;
  197.     case K_UP:        deed = ACT_UP;        break;
  198.     case K_DOWN:        deed = ACT_DOWN;    break;
  199.     case K_PAGE_UP:        deed = ACT_PAGE_UP;    break;
  200.     case K_PAGE_DOWN:    deed = ACT_PAGE_DOWN;    break;
  201.     case K_HOME:        deed = ACT_TOP_EDGE;    break;
  202.     case K_END:        deed = ACT_BOT_EDGE;    break;
  203.     }
  204.     return deed;
  205.     }
  206.  
  207.  
  208. //-----------------------------------------------------------------------------
  209. // - classifyOtherKey:
  210. //-----------------------------------------------------------------------------
  211. - (KB_Action)classifyOtherKey:(NSEvent*)p
  212.     {
  213.     KB_Action deed = ACT_IGNORE;
  214.     switch ([[p charactersIgnoringModifiers] characterAtIndex:0])
  215.     {
  216.     case K_SPACE:        deed = ACT_SELECT;    break;
  217.     case K_RETURN:        deed = ACT_PERFORM;    break;
  218.     }
  219.     return deed;
  220.     }
  221.  
  222.  
  223. //-----------------------------------------------------------------------------
  224. // - classifyNumericPadKey:
  225. //-----------------------------------------------------------------------------
  226. - (KB_Action)classifyNumericPadKey:(NSEvent*)p
  227.     {
  228.     KB_Action deed = ACT_IGNORE;
  229.     unichar const charCode =
  230.         [[p charactersIgnoringModifiers] characterAtIndex:0];
  231.  
  232.     if (charCode == K_KP_ENTER)
  233.     deed = ACT_PERFORM;
  234.     else if ('0' <= charCode && charCode <= '9')
  235.     {
  236.     static KB_Action const ACTS[] =
  237.         {
  238.         ACT_SELECT,        // KP 0 (insert)
  239.         ACT_BOT_EDGE,    // KP 1 (end)
  240.         ACT_DOWN,        // KP 2 (arrow down)
  241.         ACT_PAGE_DOWN,    // KP 3 (page down)
  242.         ACT_LEFT,        // KP 4 (arrow left)
  243.         ACT_IGNORE,        // KP 5
  244.         ACT_RIGHT,        // KP 6 (arrow right)
  245.         ACT_TOP_EDGE,    // KP 7 (home)
  246.         ACT_UP,        // KP 8 (arrow up)
  247.         ACT_PAGE_UP        // KP 9 (page up)
  248.         };
  249.     deed = ACTS[ charCode - '0' ];
  250.     }
  251.     return deed;
  252.     }
  253.  
  254.  
  255. //-----------------------------------------------------------------------------
  256. // - classifyFlags:forAction:
  257. //-----------------------------------------------------------------------------
  258. - (KB_Action)classifyFlags:(int)flags forAction:(KB_Action)deed
  259.     {
  260.     static KB_Action const MODIFIED_ACTIONS[ ACT_NUM_ACTIONS ] =
  261.     {
  262. //--    Becomes...        Was...        --//
  263.     ACT_IGNORE,        // ACT_IGNORE
  264.     ACT_SELECT,        // ACT_SELECT
  265.     ACT_PERFORM,        // ACT_PERFORM
  266.     ACT_PAGE_LEFT,        // ACT_LEFT
  267.     ACT_PAGE_RIGHT,        // ACT_RIGHT
  268.     ACT_PAGE_UP,        // ACT_UP
  269.     ACT_PAGE_DOWN,        // ACT_DOWN
  270.     ACT_PAGE_LEFT,        // ACT_PAGE_LEFT
  271.     ACT_PAGE_RIGHT,        // ACT_PAGE_RIGHT
  272.     ACT_PAGE_LEFT,        // ACT_PAGE_UP
  273.     ACT_PAGE_RIGHT,        // ACT_PAGE_DOWN
  274.     ACT_LEFT_EDGE,        // ACT_LEFT_EDGE
  275.     ACT_RIGHT_EDGE,        // ACT_RIGHT_EDGE
  276.     ACT_LEFT_EDGE,        // ACT_TOP_EDGE
  277.     ACT_RIGHT_EDGE        // ACT_BOT_EDG
  278.     };
  279.     int const FLAGS = NSControlKeyMask | NSAlternateKeyMask | NSShiftKeyMask;
  280.     if ((flags & FLAGS) != 0)
  281.     return MODIFIED_ACTIONS[ deed ];
  282.     return deed;
  283.     }
  284.  
  285.  
  286. //-----------------------------------------------------------------------------
  287. // - classifyKeyDown:
  288. //-----------------------------------------------------------------------------
  289. - (KB_Action)classifyKeyDown:(NSEvent*)p
  290.     {
  291.     KB_Action deed = ACT_IGNORE;
  292.     unsigned int const flags = [p modifierFlags];
  293.     if ((flags & NSCommandKeyMask) == 0)
  294.     {
  295.     if ((flags & NSFunctionKeyMask) != 0)
  296.         deed = [self classifyFunctionKey:p];
  297.     else if ((flags & NSNumericPadKeyMask) != 0)
  298.         deed = [self classifyNumericPadKey:p];
  299.     else
  300.         deed = [self classifyOtherKey:p];
  301.  
  302.     if (deed != ACT_IGNORE)
  303.         deed = [self classifyFlags:flags forAction:deed];
  304.     }
  305.     return deed;
  306.     }
  307.  
  308.  
  309. //-----------------------------------------------------------------------------
  310. // - keyDown:
  311. //-----------------------------------------------------------------------------
  312. - (void)keyDown:(NSEvent*)p 
  313.     {
  314.     KB_Action deed = [self classifyKeyDown:p];
  315.     BOOL handled = (deed != ACT_IGNORE);
  316.     if (handled)
  317.     {
  318.     switch (deed)
  319.         {
  320.         case ACT_SELECT:    [self keyboardSelect:p];        break;
  321.         case ACT_PERFORM:    [self sendDoubleActionIfEnabled];    break;
  322.         case ACT_UP:    [tableView moveCursorBy:-1];        break;
  323.         case ACT_DOWN:    [tableView moveCursorBy: 1];        break;
  324.         case ACT_LEFT:    [tableView moveCursorBy:-1];        break;
  325.         case ACT_RIGHT:    [tableView moveCursorBy: 1];        break;
  326.         case ACT_PAGE_LEFT:    [self goPrevPage: MISC_COL_BORDER];    break;
  327.         case ACT_PAGE_RIGHT:[self goNextPage: MISC_COL_BORDER];    break;
  328.         case ACT_PAGE_UP:    [self goPrevPage: MISC_ROW_BORDER];    break;
  329.         case ACT_PAGE_DOWN:    [self goNextPage: MISC_ROW_BORDER];    break;
  330.         case ACT_LEFT_EDGE:    [self goFirstSlot:MISC_COL_BORDER];    break;
  331.         case ACT_RIGHT_EDGE:[self goLastSlot: MISC_COL_BORDER];    break;
  332.         case ACT_TOP_EDGE:    [self goFirstSlot:MISC_ROW_BORDER];    break;
  333.         case ACT_BOT_EDGE:    [self goLastSlot: MISC_ROW_BORDER];    break;    
  334.         default:        handled = NO;                break;
  335.         }
  336.     }
  337.  
  338.     if (!handled && ![self incrementalSearch:p])
  339.     [self superKeyDown:p];
  340.     }
  341.  
  342. @end
  343.