/*-- AutoRev header do NOT edit! * * Program : event.c * Copyright : © 1991 Jaba Development * Author : Jan van den Baard * Creation Date : 21-Apr-91 * Current version : 1.0 * Translator : DICE v2.6 * * REVISION HISTORY * * Date Version Comment * --------- ------- ------------------------------------------ * 21-Apr-91 1.0 View keyboard event-handler + subs. * *-- REV_END --*/ #include "view.h" /* * All kinds of qualifier-key combinations. */ #define MOUSE IEQUALIFIER_RELATIVEMOUSE #define REPEAT IEQUALIFIER_REPEAT #define LOCK IEQUALIFIER_CAPSLOCK #define NUMPAD IEQUALIFIER_NUMERICPAD #define LSHIFT IEQUALIFIER_LSHIFT #define RSHIFT IEQUALIFIER_RSHIFT #define CONTROL IEQUALIFIER_CONTROL #define NORM1 MOUSE #define NORM2 NORM1+REPEAT #define NORM3 NORM1+LOCK #define NORM4 NORM2+LOCK #define NUMP1 MOUSE+NUMPAD #define NUMP2 NUMP1+REPEAT #define NUMP3 NUMP1+LOCK #define NUMP4 NUMP2+LOCK #define CTRL1 MOUSE+CONTROL #define CTRL2 CTRL1+REPEAT #define CTRL3 CTRL1+LOCK #define CTRL4 CTRL2+LOCK #define PRIN1 CTRL1+LSHIFT #define PRIN2 CTRL3+LSHIFT #define SHIF1 MOUSE+LSHIFT #define SHIF2 MOUSE+RSHIFT #define SHIF3 SHIF1+REPEAT #define SHIF4 SHIF2+REPEAT #define SHIF5 SHIF1+LOCK #define SHIF6 SHIF2+LOCK #define SHIF7 SHIF3+LOCK #define SHIF8 SHIF4+LOCK /* * hot-keys to be pressed together with LALT+LAMIGA * when view is taking a nap. */ #define VIEW 0x34 #define QUIT 0x10 #define FLUSH 0x23 /* * some external referenced globals. */ extern APTR ConsoleDevice; extern ULONG VW_class; extern UWORD VW_qual, VW_code, VW_pmark; extern UWORD VW_mode, VW_pmode, VW_printing, VW_err; extern UBYTE ClearStr[]; extern struct Screen *VW_scr; /* * some external referenced function proto-types. */ extern __regargs void Quit( long ); extern __regargs void Inform( char *); extern void LineUp( void ); extern void LineDown( void ); extern void DisplayText( void ); extern void Top( void ); extern void Bottom( void ); extern void PageUp( void ); extern void PageDown( void ); extern __regargs void LoadFile( long ); extern void Help( void ); extern void DoFound( void ); extern __regargs void GetSomething( ULONG ); extern void FindN( void ); extern void FindP( void ); extern void PrintFile( void ); extern __regargs void Sleep( BOOL ); extern void InfoLine( void ); extern void EditFile( void ); extern __regargs void SetMark( UWORD ); extern __regargs void UnSetMark( UWORD ); extern __regargs void JumpMark( UWORD ); /* * some local proto-types. */ void ConvertKeyTab( void ); __regargs void HandleKeyboard( UWORD, UWORD ); __regargs void SteadyRepeat( struct MsgPort * ); __regargs long HandleMsg( struct MsgPort * ); __regargs void ClearMsg( struct MsgPort * ); /* * "__stkargs" because it uses the stub routine * from "hstub.s" to set-up it's arguments on stack. */ __stkargs struct InputEvent *ViewHandler( struct InputEvent *, struct HandlerMuck * ); /* * Vanilla key-codes normal and shifted. */ UBYTE KeyTable[64]; UBYTE SKeyTable[64]; /* * Setup a key-table for normal and shifted key codes so * View will work with all kinds of foreigh key-mappings. */ void ConvertKeyTab() { struct InputEvent ievent; UWORD i; setmem(&ievent,sizeof(struct InputEvent),0); ievent.ie_Class = IECLASS_RAWKEY; for(i=0;i<64;i++) { /* build normal key-table */ ievent.ie_Code = i; RawKeyConvert(&ievent,&KeyTable[i],1,NULL); } ievent.ie_Qualifier = LSHIFT; for(i=0;i<64;i++) { /* build shifted key-table */ ievent.ie_Code = i; RawKeyConvert(&ievent,&SKeyTable[i],1,NULL); } } /* * Prevent a overhead of RAWKEY message with * the REPEAT qualifier. It deletes all but one * RAWKEY messages with the REPEAT qualifier * set. The one REPEAT message left then get's * interpreted by the main loop. This ensures * that the text won't scroll more than one * page to far after the keys are released. */ __regargs void SteadyRepeat( port ) struct MsgPort *port; { struct IntuiMessage *m1, *m2; Forbid(); /* don't race intuition */ m1 = (struct IntuiMessage *)port->mp_MsgList.lh_Head; while(m2 = (struct IntuiMessage *)m1->ExecMessage.mn_Node.ln_Succ) { if(!m2->ExecMessage.mn_Node.ln_Succ) break; if(m1->Class != IDCMP_RAWKEY) break; if(!(m1->Qualifier & REPEAT)) break; if(m2->Class != IDCMP_RAWKEY) break; if(!(m2->Qualifier & REPEAT)) break; ReplyMsg(GetMsg(port)); m1 = (struct IntuiMessage *)port->mp_MsgList.lh_Head; } Permit(); } /* * Get and interpred a message from the port. * return TRUE if there was a message received * or FALSE if not. */ __regargs long HandleMsg( struct MsgPort *port ) { struct IntuiMessage *msg; if((msg = GT_GetIMsg(port))) { /* gotten a message! */ VW_class = msg->Class; VW_code = msg->Code; VW_qual = msg->Qualifier; GT_ReplyIMsg(msg); /* gadtools is open so why not... */ return TRUE; } return FALSE; } /* * Reply all pending messages on the msgport * without doing something with them. */ __regargs void ClearMsg( struct MsgPort *port ) { struct IntuiMessage *msg; Forbid(); /* don't race intuition. */ while(msg = GT_GetIMsg(port)) GT_ReplyIMsg(msg); Permit(); } /* * This is the input-handler which, if active, looks for * wake-up signals. This routine uses the hard-coded keyboard * layout instead of the "Vanilla one". */ __stkargs __geta4 struct InputEvent *ViewHandler( struct InputEvent *event, struct HandlerMuck *data) { struct InputEvent *ev; for(ev = event; ev; ev = ev->ie_NextEvent) { if(ev->ie_Class == IECLASS_RAWKEY) { /* only RAWKEY events */ if((ev->ie_Qualifier & IEQUALIFIER_LALT) && (ev->ie_Qualifier & IEQUALIFIER_LCOMMAND)) { switch(ev->ie_Code) { /* look what key was used */ case VIEW: ev->ie_Class = IECLASS_NULL; data->View = TRUE; data->Quit = FALSE; data->Flush = FALSE; goto SigIT; break; case QUIT: ev->ie_Class = IECLASS_NULL; data->View = FALSE; data->Quit = TRUE; data->Flush = FALSE; goto SigIT; break; case FLUSH: ev->ie_Class = IECLASS_NULL; data->View = FALSE; data->Quit = FALSE; data->Flush = TRUE; SigIT: Signal(data->ViewTask,data->ViewSigMask); break; default: break; } } } } return(event); } /* * Handle all incoming RAWKEY messages. */ __regargs void HandleKeyboard( code, qualifier ) UWORD code, qualifier; { if((code & IECODE_UP_PREFIX) != IECODE_UP_PREFIX) { /* only key-down */ if(VW_err) InfoLine(); /* refresh info line if needed */ switch(qualifier) { case NORM1: case NORM2: case NORM3: case NORM4: /* normal key without qualifier keys */ if(code < 64) { switch(KeyTable[code]) { /* keymap keys */ case 'h': Help(); break; case 'q': if(!VW_printing) Quit( RETURN_OK ); break; case '/': case 'f': VW_mode = TRUE; GetSomething(STRING_KIND); break; case '.': case 's': VW_mode = FALSE; GetSomething(STRING_KIND); break; case 'n': VW_mode = TRUE; FindN(); break; case 'p': VW_mode = TRUE; FindP(); break; case 'r': Inform(ClearStr); DisplayText(); break; case 'e': EditFile(); break; case 'l': if(!VW_printing) LoadFile(TRUE); break; case 'j': DoFound(); break; case 'b': if(!VW_printing) Sleep(FALSE); break; default: break; } } else if(code >= 0x50 && code <= 0x59) { /* function keys */ SetMark((UWORD)(code - 0x50)); break; } else { switch(code) { /* RAW keys (the same on any Amiga..?) */ case 0x40: /* Space bar */ PageDown(); break; case 0x41: /* BackSpace */ PageUp(); break; case 0x4d: /* Down arrow */ case 0x44: /* Return */ LineDown(); break; case 0x4c: /* Up arrow */ LineUp(); break; case 0x5f: /* Help */ Help(); break; case 0x45: /* Esc */ if(!VW_printing) Quit( RETURN_OK ); break; default: break; } } break; case NUMP1: case NUMP2: case NUMP3: case NUMP4: /* Numeric key-pad */ if(code < 64) { /* keymap keys */ switch(KeyTable[code]) { case '7': case '4': Top(); break; case '1': case '6': Bottom(); break; case '8': LineUp(); break; case '2': LineDown(); break; case '9': PageUp(); break; case '3': PageDown(); break; default: break; } } else if(code == 0x43) { /* Enter */ LineUp(); break; } break; case CTRL1: case CTRL2: case CTRL3: case CTRL4: /* key with CTRL */ if(code < 64) { /* keymap keys */ switch(KeyTable[code]) { case 'c': if(!VW_printing) Quit( RETURN_OK ); break; case 'n': VW_mode = FALSE; FindN(); break; case 'p': VW_mode = FALSE; FindP(); break; case 'l': Inform(ClearStr); DisplayText(); break; case 'b': if(!VW_printing) Sleep(TRUE); break; default: break; } } else if(code >= 0x50 && code <= 0x59) { /* Function keys */ JumpMark((UWORD)(code - 0x50)); break; } break; case PRIN1: case PRIN2: /* LEFT_SHIFT + CONTROL + key */ if(code < 64) { /* keymap keys */ switch(KeyTable[code]) { case 'd': if(!VW_printing) { VW_pmode = PRT_PAGE; PrintFile(); } break; case 'p': if(!VW_printing) { VW_pmode = PRT_FILE; PrintFile(); } break; default: break; } } else if(code >= 0x50 && code <= 0x59) { /* Function keys */ VW_pmode = PRT_BLOCK; VW_pmark = (UWORD)(code - 0x50); PrintFile(); break; } break; case SHIF1: case SHIF2: case SHIF3: case SHIF4: case SHIF5: case SHIF6: case SHIF7: case SHIF8: /* SHIFT + key */ if(code < 64) { /* keymap key */ switch(SKeyTable[code]) { case '<': Top(); break; case '>': Bottom(); break; case '%': GetSomething(INTEGER_KIND); break; default: break; } } else if(code >= 0x50 && code <= 0x59) { /* Function keys */ UnSetMark((UWORD)(code - 0x50)); break; } default: break; } } } }