home *** CD-ROM | disk | FTP | other *** search
/ Fresh Fish 1 / FFMCD01.bin / bbs / libdisks / d700t799 / disk793.lha / Snap / src.lha / src / snap.c < prev    next >
Encoding:
C/C++ Source or Header  |  1992-12-15  |  40.9 KB  |  1,248 lines

  1. /***********************************************\
  2. *                                               *
  3. *                     Snap                      *
  4. *         © Mikael Karlsson 1988-1991           *
  5. *                                               *
  6. \***********************************************/
  7. /* Auto: make "CCEXTRA=-wq -qf"
  8. */
  9.  
  10. #ifdef SNAPREXX
  11. #include "minrexx.h"
  12. #endif SNAPREXX
  13. #include <stdio.h>
  14.  
  15. #define ARGVAL() ((*argv && *++(*argv)) || (--argc && *++argv))
  16.  
  17. static char Version[] = "$VER: 1.63 © 1991 Mikael Karlsson & Absolut Software\n";
  18.  
  19. BOOL Kick36;
  20.  
  21. /* signals */
  22. LONGBITS startsignal, insertsignal, cancelsignal;
  23. LONGBITS donesignal, movesignal, clicksignal;
  24. LONGBITS timersignal, initsignal, cwsignal, ticksignal;
  25. ULONG startsignum = -1L;
  26. ULONG insertsignum = -1L;
  27. ULONG cancelsignum = -1L;
  28. ULONG donesignum = -1L;
  29. ULONG movesignum = -1L;
  30. ULONG clicksignum = -1L;
  31. ULONG initsignum = -1L;
  32. ULONG cwsignum = -1L;
  33. ULONG ticksignum = -1L;
  34. ULONG WaitSignal;
  35.  
  36. /* program */
  37. struct SnapRsrc *SnapRsrc = NULL;
  38. struct Task *MyTask;
  39.  
  40. /* Snap state machine */
  41. WORD action;
  42. WORD state;
  43.  
  44. /* clipboard */
  45. struct IOClipReq *ClipReq = NULL;
  46. struct MsgPort *ClipPort = NULL;
  47.  
  48. /* timer device */
  49. struct MsgPort *TimerPort = NULL;
  50. struct timerequest MyTR;
  51.  
  52. /* input device */
  53. struct MsgPort *inputDevPort = NULL;
  54. struct Interrupt handlerStuff;
  55. struct IOStdReq *inputRequestBlock = NULL;
  56. struct InputEvent SimEvent;
  57. WORD textqual;
  58. WORD gfxqual;
  59. WORD insertkey;
  60. WORD cwkey;
  61. WORD modinsert;
  62.  
  63. UBYTE *CharData = NULL;
  64. UBYTE TrueUnderscore;
  65.  
  66. /* console */
  67. struct MsgPort *ConPort = NULL;
  68. struct IOStdReq *ConIOR = NULL;
  69. struct KeyMap keymap;
  70.  
  71. /* windows */
  72. #ifdef SNAPGFX
  73. struct MsgPort *Sharedport = NULL;
  74. SHORT Sharedrefs;
  75. IMPORT struct Window *ControlWindow;
  76. struct Window *SaveWin = NULL;
  77. IMPORT struct Gadget SaveGad;
  78. IMPORT struct Gadget NameGad;
  79. struct GfxSnap *SwapGS = NULL;
  80. IMPORT struct StringInfo TranspSI;
  81. IMPORT struct Image ActiveDiskImage;
  82. IMPORT struct Image InactiveDiskImage;
  83. IMPORT struct Image ActiveClipImage;
  84. IMPORT struct Image InactiveClipImage;
  85. #endif SNAPGFX
  86. IMPORT UBYTE *WindowTitle;
  87.  
  88. /* libraries */
  89. IMPORT struct ExecBase *SysBase;
  90. struct IntuitionBase *IntuitionBase = NULL;
  91. struct GfxBase       *GfxBase = NULL;
  92. struct LayersBase    *LayersBase = NULL;
  93. struct DiskFontBase  *DiskfontBase = NULL;
  94. struct Library       *IconBase = NULL;
  95. #ifdef SNAPGFX
  96. #ifdef REQLIB
  97. struct ReqBase       *ReqBase = NULL;
  98. #endif REQLIB
  99. #ifdef ASLLIB
  100. struct Library       *AslBase = NULL;
  101. #endif ASLLIB
  102. #endif SNAPGFX
  103.  
  104. /* graphics */
  105. struct Screen *theScreen;
  106. struct Layer *theLayer;
  107. struct RastPort rp, TempRp, MyRP;
  108. struct BitMap TempBM, MyBM;
  109. UBYTE *TempRaster = NULL;
  110.  
  111. #ifdef SNAPGFX
  112. #ifdef REQLIB
  113. struct ReqFileRequester *NameFR = NULL;
  114. #endif REQLIB
  115. #ifdef ASLLIB
  116. struct FileRequester *AslNameFR = NULL;
  117. #endif ASLLIB
  118. char SaveName[DSIZE+FCHARS+2];
  119. BPTR SnapFile;
  120. #endif SNAPGFX
  121.  
  122. /* ARexx stuff */
  123. #ifdef SNAPREXX
  124. ULONG rexxsignal;
  125. IMPORT struct rexxCommandList rcl[];
  126. WORD disp();
  127. #endif SNAPREXX
  128.  
  129. #ifdef AZTEC_C
  130. int stricmp(char *s1, char *s2 )
  131. {
  132.    char c1, c2;
  133.  
  134.    while (*s1 && *s2) {
  135.       if ((c1 = *(s1++)) >= 'a' && c1 <= 'z') {
  136.          c1 -= 32;
  137.       }
  138.       if ((c2 = *(s2++)) >= 'a' && c2 <= 'z') {
  139.          c2 -= 32;
  140.       }
  141.  
  142.       if ( c1 != c2 ) {
  143.          return( c1 - c2 );
  144.       }
  145.    }
  146.  
  147.    return( *s1 - *s2 );
  148. }
  149.  
  150.  
  151. int strnicmp(char *s1, char *s2, int n)
  152. {
  153.    char c1, c2;
  154.  
  155.    while (*s1 && *s2 && --n > 0) {
  156.       c1 = *(s1++);
  157.       c2 = *(s2++);
  158.  
  159.       if (c1 >= 'a' && c1 <= 'z') {
  160.          c1 -= 32;
  161.       }
  162.       if (c2 >= 'a' && c2 <= 'z') {
  163.          c2 -= 32;
  164.       }
  165.  
  166.       if (c1 != c2) {
  167.          return(c1 - c2);
  168.       }
  169.    }
  170.  
  171.    c1 = *s1;
  172.    c2 = *s2;
  173.  
  174.    if (c1 >= 'a' && c1 <= 'z') {
  175.       c1 -= 32;
  176.    }
  177.    if (c2 >= 'a' && c2 <= 'z') {
  178.       c2 -= 32;
  179.    }
  180.  
  181.    return(c1 - c2);
  182. }
  183. #endif
  184.  
  185. LONG dectoint(REGISTER char *str)
  186. {
  187.     REGISTER long val = 0;
  188.     REGISTER char c;
  189.     while ((c = *str) >= '0' && c <= '9') {
  190.         val = (((val<<2)+val)<<1) + c-'0';
  191.         str++;
  192.     }
  193.     return(val);
  194. }
  195.  
  196. LONG hextoint(REGISTER char *str)
  197. {
  198.     REGISTER long val = 0;
  199.     REGISTER char c;
  200.  
  201.     if (!strnicmp(str, "0x", 2)) {
  202.         str += 2;
  203.     }
  204.     while (c = *str) {
  205.         val <<= 4;
  206.         val |= (c & 15) + ((c>='0' && c<='9') ? 0 : 9);
  207.         str++;
  208.     }
  209.     return(val);
  210. }
  211.  
  212. WORD insertcount;
  213.  
  214. VOID InsertAscii(ULONG ascii)
  215. {
  216.     if (insertcount == 1) {   /* Time for second char */
  217.           /* Not necessary to patch here but it guarantees
  218.              that all inserted chars end up in the same window. */
  219.         SafePatch();
  220.     }
  221.     if (AsciiToInputEvent(ascii, &SimEvent, &keymap)) {
  222.         DoIO((struct IORequest *)inputRequestBlock);
  223.         if (SnapRsrc->chardelay) {
  224.             MyTR.tr_node.io_Command = TR_ADDREQUEST;
  225.             MyTR.tr_time.tv_micro = SnapRsrc->chardelay;
  226.             MyTR.tr_time.tv_secs = 0;
  227.             DoIO((struct IORequest *)&MyTR);
  228.         }
  229.     }
  230.     ++insertcount;
  231. }
  232.  
  233. #ifdef SNAPGFX
  234. VOID GadText(struct Gadget *Gad, char *Str, LONG Len)
  235. {
  236.     char temp[256];
  237.     SHORT i;
  238.  
  239.     SetDrMd(ControlWindow->RPort, JAM2);
  240.     SetAPen(ControlWindow->RPort, 0L);
  241.     RectFill(ControlWindow->RPort, (LONG)Gad->LeftEdge, (LONG)Gad->TopEdge,
  242.       (LONG)Gad->LeftEdge + Gad->Width - 1, (LONG)Gad->TopEdge + Gad->Height - 1);
  243.     SetAPen(ControlWindow->RPort, 1L);
  244.     SetBPen(ControlWindow->RPort, 0L);
  245.     Move(ControlWindow->RPort,
  246.       (LONG)Gad->LeftEdge + 1,
  247.       (LONG)Gad->TopEdge + ControlWindow->RPort->Font->tf_Baseline + 1);
  248.     if (TextLength(ControlWindow->RPort, Str, Len) > Gad->Width) {
  249.         i = Len;
  250.         strncpy(temp, Str, i - 3);
  251.         strcat(temp, "...");
  252.         while (TextLength(ControlWindow->RPort, temp, (LONG)i) > Gad->Width) {
  253.             --i;
  254.             temp[i] = '\0';
  255.             temp[i-3] = '.';
  256.         }
  257.         Text(ControlWindow->RPort, temp, (LONG)i);
  258.     } else {
  259.         Text(ControlWindow->RPort, Str, Len);
  260.     }
  261. }
  262.  
  263. VOID SwapColorMap(struct GfxSnap *GS)
  264. {
  265.     struct ViewPort *vp = &GS->window->WScreen->ViewPort;
  266.     LONG i = (GS->viewmode & HAM ? 16 : 1L << GS->depth);
  267.     ULONG col;
  268.  
  269.     while (i-- && (col = GetRGB4(vp->ColorMap, i)) != -1L) {
  270.         SetRGB4(vp, i,
  271.           (LONG)GS->rgb[i][0] >> 4,
  272.           (LONG)GS->rgb[i][1] >> 4,
  273.           (LONG)GS->rgb[i][2] >> 4);
  274.         GS->rgb[i][0] = ((col >> 8) & 0x0f) << 4;
  275.         GS->rgb[i][1] = ((col >> 4) & 0x0f) << 4;
  276.         GS->rgb[i][2] = ((col >> 0) & 0x0f) << 4;
  277.     }
  278. }
  279.  
  280. VOID CheckWindowMsgs()
  281. {
  282.     struct IntuiMessage *Msg;
  283.     struct IntuiMessage *QdMsg = NULL;
  284.     ULONG Class;
  285.     USHORT Code;
  286.     struct Window *Win;
  287.     struct Gadget *Gad;
  288.  
  289.     while (Sharedport &&
  290.       (QdMsg || (Msg = (struct IntuiMessage *)GetMsg(Sharedport)))) {
  291.         if (QdMsg) {
  292.             Msg = QdMsg;
  293.             QdMsg = NULL;
  294.         }
  295.         Class = Msg->Class;
  296.         Code  = Msg->Code;
  297.         Win   = Msg->IDCMPWindow;
  298.         Gad   = (struct Gadget *)Msg->IAddress;
  299.         ReplyMsg((struct Message *)Msg);
  300.         switch (Class) {
  301.             case CLOSEWINDOW: {
  302.                 struct GfxSnap *GS = NULL;
  303.                 if (Win == ControlWindow) {
  304.                     ControlWindow = NULL;
  305.                     if (SaveWin) {
  306.                         SetWindowTitles(SaveWin, (char *)WindowTitle, (char *)-1);
  307.                         SaveWin = NULL;
  308.                     }
  309.                 } else {
  310.                     GS = (struct GfxSnap *)Win->UserData;
  311.                     FreePlanes(&GS->BM, GS->width, GS->height);
  312.                     if (Win == SaveWin || Sharedrefs == 1) {
  313.                         if (ControlWindow) {
  314.                             OffGadget(&SaveGad, ControlWindow, NULL);
  315.                         }
  316.                         SaveWin = NULL;
  317.                     }
  318.                 }
  319.                 closesharedwindow(Win);
  320.                 if (GS) {
  321.                     Kill(GS);
  322.                 }
  323.                 break;
  324.             }
  325.             case NEWSIZE: {
  326.                 AdjustSize((struct GfxSnap *)Win->UserData);
  327.                 break;
  328.             }
  329.             case MOUSEMOVE: {
  330.                   /* Collapse all consecutively queued MOUSEMOVE msgs */
  331.                 while ((QdMsg = (struct IntuiMessage *)GetMsg(Sharedport))
  332.                   && (QdMsg->Class == MOUSEMOVE)) {
  333.                     ReplyMsg((struct Message *)QdMsg);
  334.                 }
  335.                 SyncGS((struct GfxSnap *)Win->UserData);
  336.                 break;
  337.             }
  338.             case REFRESHWINDOW: {
  339.                 BeginRefresh(Win);
  340.                 SyncGS((struct GfxSnap *)Win->UserData);
  341.                 EndRefresh(Win, 1L);
  342.             }
  343.             case INACTIVEWINDOW: {
  344.                 if (Win != ControlWindow) {
  345.                     struct GfxSnap *GS;
  346.                     GS = (struct GfxSnap *)Win->UserData;
  347.                     if (SwapGS) {
  348.                         SwapColorMap(SwapGS);
  349.                         SwapGS = NULL;
  350.                     }
  351.                     GS->DiskGad.GadgetRender = (APTR)&InactiveDiskImage;
  352.                     GS->ClipGad.GadgetRender = (APTR)&InactiveClipImage;
  353.                     RefreshGList(&GS->DiskGad, GS->window, NULL, -1);
  354.                 }
  355.                 break;
  356.             }
  357.             case ACTIVEWINDOW: {
  358.                 if (Win != ControlWindow) {
  359.                     struct GfxSnap *GS;
  360.                     GS = (struct GfxSnap *)Win->UserData;
  361.                     GS->DiskGad.GadgetRender = (APTR)&ActiveDiskImage;
  362.                     GS->ClipGad.GadgetRender = (APTR)&ActiveClipImage;
  363.                     RefreshGList(&GS->DiskGad, GS->window, NULL, -1);
  364.                 }
  365.                 break;
  366.             }
  367.             case GADGETUP: {
  368.                 switch (Gad->GadgetID) {
  369.                     case VPROP:
  370.                     case HPROP: {
  371.                         SyncGS((struct GfxSnap *)Win->UserData);
  372.                         break;
  373.                     }
  374.                     case SAVEGAD: {
  375. savepic:
  376.                         if (SaveWin) {
  377.                             WORD success = 0;
  378.                             struct GfxSnap *GS;
  379.                             GS = (struct GfxSnap *)SaveWin->UserData;
  380.  
  381.                             if (SaveName[0] == '\0') {
  382.                                 DisplayBeep(NULL);
  383.                                 ActivateGadget(&NameGad, ControlWindow, NULL);
  384.                                 break;
  385.                             }
  386.                             SnapFile = (BPTR)Open((char *)SaveName, MODE_NEWFILE);
  387.                             if (SnapFile) {
  388.                                 struct CBFHandle CBFH;
  389.                                 CBFH.Type = CBFFILE;
  390.                                 CBFH.Handle.File = SnapFile;
  391.                                 success = SaveGS(GS, &CBFH);
  392.                                 Close(SnapFile);
  393.                             }
  394.                             if (success) {
  395.                                 SetWindowTitles(ControlWindow, "Saved ok", (char *)-1);
  396.                             } else {
  397.                                 DeleteFile((char *)SaveName);
  398.                                 DisplayBeep(NULL);
  399.                                 SetWindowTitles(ControlWindow, "Save failed", (char *)-1);
  400.                             }
  401.                         }
  402.                         break;
  403.                     }
  404.                     case NAMEGAD: { /* Should only happen with Req */
  405. #ifdef ASLLIB
  406.                         if ((AslNameFR) && (Kick36)) {
  407.                             if (RequestFile(AslNameFR)) {
  408.                                 strncpy(SaveName, AslNameFR->rf_Dir, sizeof(SaveName));
  409.                                 AddPart((UBYTE *)SaveName,
  410.                                         (UBYTE *)AslNameFR->rf_File,
  411.                                         sizeof(SaveName));
  412.                             }
  413.                             GadText(&NameGad, SaveName, (LONG)strlen(SaveName));
  414.                         }
  415. #else
  416.                         if (0) {}
  417. #endif ASLLIB
  418. #ifdef REQLIB
  419.                         else if (NameFR) {
  420.                             NameFR->Title = "Save picture as...";
  421.                             NameFR->PathName = SaveName;
  422.                             NameFR->Window = ControlWindow;
  423.                             (VOID)BruceFileRequester(NameFR);
  424.                             GadText(&NameGad, SaveName, (LONG)strlen(SaveName));
  425.                         }
  426. #endif REQLIB
  427.                         break;
  428.                     }
  429.                     case DISKGAD: {
  430.                         struct GfxSnap *GS;
  431.                         if (!ControlWindow && !OpenCW()) {
  432.                             DisplayBeep(NULL);
  433.                             break;
  434.                         }
  435.                         if (Win == SaveWin) {
  436.                             goto savepic;
  437.                         }
  438.                         if (SaveWin) {
  439.                             SetWindowTitles(SaveWin, (char *)WindowTitle, (char *)-1);
  440.                             GS = (struct GfxSnap *)SaveWin->UserData;
  441.                             RefreshGList(&GS->DiskGad, GS->window, NULL, 1L);
  442.                         } else {
  443.                             GadText(&SaveGad, "Save", 4L);
  444.                             OnGadget(&SaveGad, ControlWindow, NULL);
  445.                         }
  446.                         SaveWin = Win;
  447.                         SetWindowTitles(SaveWin, "Selected", (char *)-1);
  448.                         GS = (struct GfxSnap *)SaveWin->UserData;
  449.                         RefreshGList(&GS->DiskGad, GS->window, NULL, 1L);
  450.                         break;
  451.                     }
  452.                     case CLIPGAD: {
  453.                         struct CBFHandle CBFH;
  454.                         struct GfxSnap *GS = (struct GfxSnap *)Win->UserData;
  455.  
  456.                         CBFH.Type = CBFCLIP;
  457.                         CBFH.Handle.ClipReq = ClipReq;
  458.                         if (!SaveGS(GS, &CBFH)) {
  459.                             DisplayBeep(NULL);
  460.                         }
  461.                         break;
  462.                     }
  463.                     default: {
  464.                         break;
  465.                     }
  466.                 }
  467.                 break;
  468.             }
  469.             case MOUSEBUTTONS: {
  470.                 if (Win != ControlWindow) {
  471.                     if (Code == SELECTDOWN && !SwapGS) {
  472.                         SwapGS = (struct GfxSnap *)Win->UserData;
  473.                         SwapColorMap(SwapGS);
  474.                     } else if (Code == SELECTUP && SwapGS) {
  475.                         SwapColorMap(SwapGS);
  476.                         SwapGS = NULL;
  477.                     }
  478.                 }
  479.                 break;
  480.             }
  481.             default: {
  482.                 break;
  483.             }
  484.         }
  485.     }
  486.     if (QdMsg) {
  487.         ReplyMsg((struct Message *)QdMsg);
  488.     }
  489. }
  490. #endif SNAPGFX
  491.  
  492. #define WriteStr(str) fputs(str, stdout)
  493. #define WriteChar(char) fputc(char, stdout)
  494.  
  495. struct QualPair {
  496.     char *str;
  497.     WORD val;
  498. };
  499.  
  500. struct QualPair Qualifiers[] = {
  501.     { "LSHIFT",    IEQUALIFIER_LSHIFT },
  502.     { "RSHIFT",    IEQUALIFIER_RSHIFT },
  503.     { "CONTROL",   IEQUALIFIER_CONTROL },
  504.     { "LALT",      IEQUALIFIER_LALT },
  505.     { "RALT",      IEQUALIFIER_RALT },
  506.     { "LCOMMAND",  IEQUALIFIER_LCOMMAND },
  507.     { "RCOMMAND",  IEQUALIFIER_RCOMMAND },
  508.     { "MIDBUTTON", IEQUALIFIER_MIDBUTTON }
  509. };
  510.  
  511. WORD ParseQual(char *quals)
  512. {
  513.     char *temp;
  514.     WORD i;
  515.     char oldc;
  516.     WORD qual = 0;
  517.  
  518.     if (('0' >= *quals) && (*quals <= '9')) {
  519.         return hextoint(quals);
  520.     }
  521.  
  522.     while (*quals) {
  523.         temp = quals;
  524.         while ((oldc = *quals) && oldc != '+') {
  525.             quals++;
  526.         }
  527.         *quals = 0;
  528.         for (i = 0; i < (sizeof(Qualifiers) / sizeof(Qualifiers[0])); i++) {
  529.             if (!stricmp(temp, Qualifiers[i].str)) {
  530.                 qual |= Qualifiers[i].val;
  531.                 break;
  532.             }
  533.         }
  534.         if (*quals = oldc) {
  535.             quals++;
  536.         }
  537.     }
  538.     return qual;
  539. }
  540.  
  541. WORD SetAltFont(char *str)
  542. {
  543.     struct TextAttr ta;
  544.     struct TextFont *NewFont;
  545.     char temp[33];
  546.     WORD pos = 0;
  547.  
  548.     if (strlen(str) <= 32) {
  549.  
  550.         strcpy(temp, str);
  551.         ta.ta_Name = (UBYTE *)temp;
  552.         while (temp[pos] != '\0' && temp[pos] != '/') {
  553.             ++pos;
  554.         }
  555.         if (temp[pos] == '\0') {     /* No size */
  556.             ta.ta_YSize = 8;
  557.         } else {
  558.             temp[pos] = '\0';
  559.             ta.ta_YSize = dectoint(&temp[pos + 1]);
  560.         }
  561.         if (pos > 5) {
  562.             if (stricmp(&temp[pos - 5], ".font")) {
  563.                 strcpy(&temp[pos], ".font");
  564.             }
  565.         } else {
  566.             strcpy(&temp[pos], ".font");
  567.         }
  568.         ta.ta_Style = 0;
  569.         ta.ta_Flags = 0;
  570.         NewFont = SmartOpenFont(&ta);
  571.         if (NewFont) {
  572.             if (SnapRsrc->AlternateFont) {
  573.                 CacheSync(SnapRsrc->AlternateFont);
  574.                 CloseFont(SnapRsrc->AlternateFont);
  575.             }
  576.             SnapRsrc->AlternateFont = NewFont;
  577.         }
  578.     }
  579.     return (NewFont ? 1 : 0);
  580. }
  581.  
  582. struct SnapRsrc DefaultRsrc = {
  583.     { NULL, NULL, NT_RESOURCE, 0, SNAPRSRC },   /* Node */
  584.     NULL,                                       /* Task */
  585.     52,                                         /* Priority */
  586.     IEQUALIFIER_RCOMMAND,                       /* Graphics qualifier */
  587.     IEQUALIFIER_LCOMMAND,                       /* Text qualifier */
  588.     0x17,                                       /* Insert key */
  589.     0x11,                                       /* Control Window key */
  590.     { '>', ' ', 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0 },  /* Prepend */
  591.     {   0,   0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0 },  /* Append */
  592.     TRUEUNDERSCORE,                             /* Flags */
  593.     0,                                          /* Char delay */
  594.     0,                                          /* Line delay */
  595.     0x7777,                                     /* Crawl pattern */
  596.     UNIT_FRAME,                                 /* Starting unit */
  597.     1,                                          /* Frame mask */
  598.     '?',                                        /* Bad char */
  599.     10,                                         /* Cache size */
  600.     1,                                          /* Extra line spacing */
  601.     { NULL, NULL, NULL },                       /* MinList, Cached windows */
  602.     NULL                                        /* Alternate font */
  603. };
  604.  
  605. #ifdef LATTICE
  606. VOID main(int argc, char **argv)
  607. #else
  608. WORD main(int argc, char **argv)
  609. #endif
  610. {
  611.     WORD create = 0, usage = 0;
  612.  
  613. #ifdef AZTEC_C
  614.     Enable_Abort = 0;
  615. #endif AZTEC_C
  616.  
  617.     Kick36 = (SysBase->LibNode.lib_Version >= 36 ? 1 : 0);
  618.  
  619.     if (!(SnapRsrc = (struct SnapRsrc *)OpenResource(SNAPRSRC))) {
  620.         create = 1;
  621.         SnapRsrc = Create(SnapRsrc);
  622.         CopyMem((char *)&DefaultRsrc, (char *)SnapRsrc, sizeof(struct SnapRsrc));
  623.         SnapRsrc->Task = FindTask(NULL);
  624.         NewList((struct List *)&SnapRsrc->CachedWindows);
  625.         AddResource((struct MiscResource *)SnapRsrc);
  626.     }
  627.  
  628.       /* Open libraries since we might need them when parsing arguments */
  629.     if (!OpenLibs()) {
  630.         goto exitpoint;
  631.     }
  632.  
  633.     if (!argc) {    /* WB Startup */
  634.         if (!create) {     /* Second time from WB -- Remove Snap */
  635.             Signal(SnapRsrc->Task, SIGBREAKF_CTRL_C);
  636.             goto exitpoint;
  637.         } else if (IconBase) {   /* Is it possible to be started from Workbench
  638.                                     without icon.library being available. */
  639.             BPTR olddir;
  640.             struct WBStartup *wbstartup;
  641.             struct DiskObject *diskobject;
  642.             char *val;
  643.  
  644.             wbstartup = (struct WBStartup *)argv;
  645.             olddir = CurrentDir(wbstartup->sm_ArgList[0].wa_Lock);
  646.             diskobject = GetDiskObject(wbstartup->sm_ArgList[0].wa_Name);
  647.             if (!diskobject) {
  648.                 goto skipargs;
  649.             }
  650.             if (val = FindToolType(diskobject->do_ToolTypes, "PRIORITY")) {
  651.                 WORD pri = dectoint(val);
  652.                 if (pri>50 && pri<128) {
  653.                     SnapRsrc->Priority = pri;
  654.                 }
  655.             }
  656.             if (val = FindToolType(diskobject->do_ToolTypes, "TEXTQUAL")) {
  657.                 if (!(SnapRsrc->textqual = ParseQual(val))) {
  658.                     SnapRsrc->textqual = IEQUALIFIER_LCOMMAND;
  659.                 }
  660.             }
  661.             if (val = FindToolType(diskobject->do_ToolTypes, "GFXQUAL")) {
  662.                 if (!(SnapRsrc->gfxqual = ParseQual(val))) {
  663.                     SnapRsrc->gfxqual = IEQUALIFIER_RCOMMAND;
  664.                 }
  665.             }
  666.             if (val = FindToolType(diskobject->do_ToolTypes, "INSERTKEY")) {
  667.                 SnapRsrc->insertkey = hextoint(val);
  668.             }
  669.             if (val = FindToolType(diskobject->do_ToolTypes, "CWKEY")) {
  670.                 SnapRsrc->cwkey = hextoint(val);
  671.             }
  672.             if (val = FindToolType(diskobject->do_ToolTypes, "APPEND")) {
  673.                 strncpy(&SnapRsrc->Append[0], val, 16);
  674.             }
  675.             if (val = FindToolType(diskobject->do_ToolTypes, "PREPEND")) {
  676.                 strncpy(&SnapRsrc->Prepend[0], val, 16);
  677.             }
  678.             if (val = FindToolType(diskobject->do_ToolTypes, "CHARDELAY")) {
  679.                 SnapRsrc->chardelay = dectoint(val);
  680.             }
  681.             if (val = FindToolType(diskobject->do_ToolTypes, "LINEDELAY")) {
  682.                 SnapRsrc->linedelay = dectoint(val) * 1000;
  683.             }
  684.             if (val = FindToolType(diskobject->do_ToolTypes, "CRAWLPTRN")) {
  685.                 SnapRsrc->CrawlPtrn = hextoint(val);
  686.             }
  687.             if (val = FindToolType(diskobject->do_ToolTypes, "XEROX")) {
  688.                 SnapRsrc->flags |= XEROX;
  689.             }
  690.             if (val = FindToolType(diskobject->do_ToolTypes, "NOXEROX")) {
  691.                 SnapRsrc->flags &= ~XEROX;
  692.             }
  693.             if (val = FindToolType(diskobject->do_ToolTypes, "EARLYPATCH")) {
  694.                 SnapRsrc->flags |= EARLYPATCH;
  695.             }
  696.             if (val = FindToolType(diskobject->do_ToolTypes, "NOEARLYPATCH")) {
  697.                 SnapRsrc->flags &= ~EARLYPATCH;
  698.             }
  699.             if (val = FindToolType(diskobject->do_ToolTypes, "STARTUNIT")) {
  700.                 if (*val == '1') {
  701.                     SnapRsrc->StartUnit = UNIT_CHAR;
  702.                 } else {
  703.                     SnapRsrc->StartUnit = UNIT_FRAME;
  704.                 }
  705.             }
  706.             if (val = FindToolType(diskobject->do_ToolTypes, "TRUEUNDERSCORE")) {
  707.                 SnapRsrc->flags |= TRUEUNDERSCORE;
  708.             }
  709.             if (val = FindToolType(diskobject->do_ToolTypes, "FAKEUNDERSCORE")) {
  710.                 SnapRsrc->flags &= ~TRUEUNDERSCORE;
  711.             }
  712.             if (val = FindToolType(diskobject->do_ToolTypes, "JOINLONG")) {
  713.                 SnapRsrc->flags |= JOINLONG;
  714.             }
  715.             if (val = FindToolType(diskobject->do_ToolTypes, "NOJOINLONG")) {
  716.                 SnapRsrc->flags &= ~JOINLONG;
  717.             }
  718.             if (val = FindToolType(diskobject->do_ToolTypes, "SIMPLEREFRESH")) {
  719.                 SnapRsrc->flags |= SIMPLEREFRESH;
  720.             }
  721.             if (val = FindToolType(diskobject->do_ToolTypes, "SMARTREFRESH")) {
  722.                 SnapRsrc->flags &= ~SIMPLEREFRESH;
  723.             }
  724.             if (val = FindToolType(diskobject->do_ToolTypes, "PLANEMASK")) {
  725.                 SnapRsrc->FrameMask = hextoint(val);
  726.             }
  727.             if (val = FindToolType(diskobject->do_ToolTypes, "CACHESIZE")) {
  728.                 SnapRsrc->CacheSize = dectoint(val);
  729.             }
  730.             if (val = FindToolType(diskobject->do_ToolTypes, "LEADING")) {
  731.                 SnapRsrc->Leading = dectoint(val);
  732.             }
  733.             if (val = FindToolType(diskobject->do_ToolTypes, "BADCHAR")) {
  734.                 SnapRsrc->BadChar = (*val ? *val : 0);
  735.             }
  736.             if (val = FindToolType(diskobject->do_ToolTypes, "ALTFONT")) {
  737.                 SetAltFont(val);
  738.             }
  739.             FreeDiskObject(diskobject);
  740.             goto skipargs;
  741.         }
  742.     }
  743.  
  744.     if (create) {
  745.         WriteStr("Snap");
  746.         WriteStr(&Version[5]);
  747.     }
  748.  
  749.     for (argc--, argv++; argc > 0; argc--, argv++) {
  750.         if (**argv == '-') { /* Argument coming up */
  751.             switch(*++(*argv)) {
  752.                 case 'p': priority: {  /* Priority */
  753.                     if (ARGVAL()) {
  754.                         WORD pri = dectoint(*argv);
  755.                         if (pri>50 && pri<128) {
  756.                             SnapRsrc->Priority = pri;
  757.                         }
  758.                     } else {
  759.                         usage = 1;
  760.                     }
  761.                     break;
  762.                 }
  763.                 case 't': textqual: {
  764.                     if (ARGVAL()) {
  765.                         if (!(SnapRsrc->textqual = ParseQual(*argv))) {
  766.                             SnapRsrc->textqual = IEQUALIFIER_LCOMMAND;
  767.                         }
  768.                     } else {
  769.                         usage = 1;
  770.                     }
  771.                     break;
  772.                 }
  773. #ifdef SNAPGFX
  774.                 case 'g': gfxqual: {
  775.                     if (ARGVAL()) {
  776.                         if (!(SnapRsrc->gfxqual = ParseQual(*argv))) {
  777.                             SnapRsrc->gfxqual = IEQUALIFIER_RCOMMAND;
  778.                         }
  779.                     } else {
  780.                         usage = 1;
  781.                     }
  782.                     break;
  783.                 }
  784. #endif SNAPGFX
  785.                 case 'i': insertkey: {
  786.                     if (ARGVAL()) {
  787.                         SnapRsrc->insertkey = hextoint(*argv);
  788.                     } else {
  789.                         usage = 1;
  790.                     }
  791.                     break;
  792.                 }
  793. #ifdef SNAPGFX
  794.                 case 'w': cwkey: {
  795.                     if (ARGVAL()) {
  796.                         SnapRsrc->cwkey = hextoint(*argv);
  797.                     } else {
  798.                         usage = 1;
  799.                     }
  800.                     break;
  801.                 }
  802. #endif SNAPGFX
  803.                 case 'c': chardelay: {
  804.                     if (ARGVAL()) {
  805.                         SnapRsrc->chardelay = dectoint(*argv) * 1000;
  806.                     } else {
  807.                         usage = 1;
  808.                     }
  809.                     break;
  810.                 }
  811.                 case 'l': linedelay: {
  812.                     if (ARGVAL()) {
  813.                         SnapRsrc->linedelay = dectoint(*argv) * 1000;
  814.                     } else {
  815.                         usage = 1;
  816.                     }
  817.                     break;
  818.                 }
  819.                 case 'a': crawlptrn: {
  820.                     if (ARGVAL()) {
  821.                         SnapRsrc->CrawlPtrn = hextoint(*argv);
  822.                     } else {
  823.                         usage = 1;
  824.                     }
  825.                     break;
  826.                 }
  827.                 case 'X': noxerox: {
  828.                     SnapRsrc->flags &= ~XEROX;
  829.                     break;
  830.                 }
  831.                 case 'x': xerox: {
  832.                     SnapRsrc->flags |= XEROX;
  833.                     break;
  834.                 }
  835.                 case 'E': noearlypatch: {
  836.                     SnapRsrc->flags &= ~EARLYPATCH;
  837.                     break;
  838.                 }
  839.                 case 'e': earlypatch: {
  840.                     SnapRsrc->flags |= EARLYPATCH;
  841.                     break;
  842.                 }
  843.                 case 'R': fakeunderscore: {
  844.                     SnapRsrc->flags &= ~TRUEUNDERSCORE;
  845.                     break;
  846.                 }
  847.                 case 'r': realunderscore: {
  848.                     SnapRsrc->flags |= TRUEUNDERSCORE;
  849.                     break;
  850.                 }
  851.                 case 'J': nojoinlong: {
  852.                     SnapRsrc->flags &= ~JOINLONG;
  853.                     break;
  854.                 }
  855.                 case 'j': joinlong: {
  856.                     SnapRsrc->flags |= JOINLONG;
  857.                     break;
  858.                 }
  859.                 case 'A': append: {
  860.                     char *dest = &SnapRsrc->Append[0];
  861.                     if ((*argv && *++(*argv)) || (--argc && ++argv)) { /* "" is ok */
  862.                         char *src = *argv;
  863.                         WORD i = 16;
  864.                         while (*src && i--) {
  865.                             *dest++ = *src++;
  866.                         }
  867.                         *dest = '\0';
  868.                     } else {
  869.                         usage = 1;
  870.                     }
  871.                     break;
  872.                 }
  873.                 case 'P': prepend: {
  874.                     char *dest = &SnapRsrc->Prepend[0];
  875.                     if ((*argv && *++(*argv)) || (--argc && ++argv)) { /* "" is ok */
  876.                         char *src = *argv;
  877.                         WORD i = 16;
  878.                         while (*src && i--) {
  879.                             *dest++ = *src++;
  880.                         }
  881.                         *dest = '\0';
  882.                     } else {
  883.                         usage = 1;
  884.                     }
  885.                     break;
  886.                 }
  887.                 case 'u': startunit: {
  888.                     if (ARGVAL()) {
  889.                         if (**argv == '1') {
  890.                             SnapRsrc->StartUnit = UNIT_CHAR;
  891.                         } else {
  892.                             SnapRsrc->StartUnit = UNIT_FRAME;
  893.                         }
  894.                     } else {
  895.                         usage = 1;
  896.                     }
  897.                     break;
  898.                 }
  899.                 case 'b': planemask: {
  900.                     if (ARGVAL()) {
  901.                         SnapRsrc->FrameMask = hextoint(*argv);
  902.                     } else {
  903.                         usage = 1;
  904.                     }
  905.                     break;
  906.                 }
  907. #ifdef SNAPGFX
  908.                 case 's': smartrefresh: {
  909.                     SnapRsrc->flags &= ~SIMPLEREFRESH;
  910.                     break;
  911.                 }
  912.                 case 'S': simplerefresh: {
  913.                     SnapRsrc->flags |= SIMPLEREFRESH;
  914.                     break;
  915.                 }
  916. #endif SNAPGFX
  917.                 case 'C': cachesize: {
  918.                     if (ARGVAL()) {
  919.                         SnapRsrc->CacheSize = dectoint(*argv);
  920.                     } else {
  921.                         usage = 1;
  922.                     }
  923.                     break;
  924.                 }
  925.                 case 'L': leading: {
  926.                     if (ARGVAL()) {
  927.                         SnapRsrc->Leading = dectoint(*argv);
  928.                     } else {
  929.                         usage = 1;
  930.                     }
  931.                     break;
  932.                 }
  933.                 case 'B': badchar: {
  934.                     if (ARGVAL()) {
  935.                         SnapRsrc->BadChar = dectoint(*argv);
  936.                     } else {
  937.                         usage = 1;
  938.                     }
  939.                     break;
  940.                 }
  941.                 case 'F': altfont: {
  942.                     if (ARGVAL()) {
  943.                         SetAltFont(*argv);
  944.                     } else {
  945.                         usage = 1;
  946.                     }
  947.                     break;
  948.                 }
  949.                 case 'Q':
  950.                 case 'q': quit: {
  951.                     if (create) {
  952.                         goto close;
  953.                     } else {
  954.                         Signal(SnapRsrc->Task, SIGBREAKF_CTRL_C);
  955.                         goto exitpoint;
  956.                     }
  957.                 }
  958.                 case '?': {
  959.                     usage = 1;
  960.                     break;
  961.                 }
  962.                 default: {
  963.                     WriteStr("Bad option: -");
  964.                     WriteChar((int)**argv);
  965.                     WriteStr(".\n");
  966.                     usage = 1;
  967.                     break;
  968.                 }
  969.             }
  970.         } else {
  971. #ifdef SNAPGFX
  972.             char *keyword = *argv;
  973.             *argv = NULL;
  974.             if (!stricmp(keyword, "PRIORITY")) {
  975.                 goto priority;                      /* Terrible, ain't it? */
  976.             } else if (!stricmp(keyword, "TEXTQUAL")) {
  977.                 goto textqual;
  978.             } else if (!stricmp(keyword, "GFXQUAL")) {
  979.                 goto gfxqual;
  980.             } else if (!stricmp(keyword, "INSERTKEY")) {
  981.                 goto insertkey;
  982.             } else if (!stricmp(keyword, "CWKEY")) {
  983.                 goto cwkey;
  984.             } else if (!stricmp(keyword, "PREPEND")) {
  985.                 goto prepend;
  986.             } else if (!stricmp(keyword, "APPEND")) {
  987.                 goto append;
  988.             } else if (!stricmp(keyword, "CHARDELAY")) {
  989.                 goto chardelay;
  990.             } else if (!stricmp(keyword, "LINEDELAY")) {
  991.                 goto linedelay;
  992.             } else if (!stricmp(keyword, "CRAWLPTRN")) {
  993.                 goto crawlptrn;
  994.             } else if (!stricmp(keyword, "XEROX")) {
  995.                 goto xerox;
  996.             } else if (!stricmp(keyword, "NOXEROX")) {
  997.                 goto noxerox;
  998.             } else if (!stricmp(keyword, "EARLYPATCH")) {
  999.                 goto earlypatch;
  1000.             } else if (!stricmp(keyword, "NOEARLYPATCH")) {
  1001.                 goto noearlypatch;
  1002.             } else if (!stricmp(keyword, "TRUEUNDERSCORE")) {
  1003.                 goto realunderscore;
  1004.             } else if (!stricmp(keyword, "FAKEUNDERSCORE")) {
  1005.                 goto fakeunderscore;
  1006.             } else if (!stricmp(keyword, "JOINLONG")) {
  1007.                 goto joinlong;
  1008.             } else if (!stricmp(keyword, "NOJOINLONG")) {
  1009.                 goto nojoinlong;
  1010.             } else if (!stricmp(keyword, "SIMPLEREFRESH")) {
  1011.                 goto simplerefresh;
  1012.             } else if (!stricmp(keyword, "SMARTREFRESH")) {
  1013.                 goto smartrefresh;
  1014.             } else if (!stricmp(keyword, "STARTUNIT")) {
  1015.                 goto startunit;
  1016.             } else if (!stricmp(keyword, "PLANEMASK")) {
  1017.                 goto planemask;
  1018.             } else if (!stricmp(keyword, "CACHESIZE")) {
  1019.                 goto cachesize;
  1020.             } else if (!stricmp(keyword, "LEADING")) {
  1021.                 goto leading;
  1022.             } else if (!stricmp(keyword, "BADCHAR")) {
  1023.                 goto badchar;
  1024.             } else if (!stricmp(keyword, "ALTFONT")) {
  1025.                 goto altfont;
  1026.             } else if (!stricmp(keyword, "QUIT")) {
  1027.                 goto quit;
  1028.             } else if (stricmp(keyword, "?")) {
  1029.                 WriteStr("Bad switch/keyword: ");
  1030.                 WriteStr(keyword);
  1031.                 WriteStr(".\n");
  1032.             }
  1033. #endif SNAPGFX
  1034.             usage = 1;
  1035.         }
  1036.     }
  1037.  
  1038.     if (usage) {
  1039.         WriteStr("Usage:\n");
  1040. #ifdef SNAPGFX
  1041.         WriteStr(" snap -pNN -tQQ -gQQ -iXX -wXX -Pstr -Astr -cNN -lNN\n");
  1042.         WriteStr("   -aXXXX -x -X -e -E -uN -r -R -j -J -s -S -bXX -CNN\n");
  1043.         WriteStr("   -LNN -BNN -Ffont -Q\n");
  1044.         WriteStr(" or\n");
  1045.         WriteStr(" snap PRIORITY/K TEXTQUAL/K GFXQUAL/K INSERTKEY/K CWKEY/K\n");
  1046.         WriteStr("   PREPEND/K APPEND/K CHARDELAY/K LINEDELAY/K CRAWLPTRN/K\n");
  1047.         WriteStr("   XEROX/S NOXEROX/S EARLYPATCH/S NOEARLYPATCH/S STARTUNIT/K\n");
  1048.         WriteStr("   TRUEUNDERSCORE/S FAKEUNDERSCORE/S JOINLONG/S NOJOINLONG/S\n");
  1049.         WriteStr("   SIMPLEREFRESH/S SMARTREFRESH/S PLANEMASK/K CACHESIZE/K\n");
  1050.         WriteStr("   LEADING/K BADCHAR/K ALTFONT/K QUIT/S\n");
  1051. #else
  1052.         WriteStr(" snap -pNN -tQQ -iXX -Pstr -Astr -cNN -lNN\n");
  1053.         WriteStr("   -aXXXX -x -X -e -E -uN -r -R -j -J -bXX -CNN\n");
  1054.         WriteStr("   -LNN -BNN -Ffont -Q\n");
  1055. #endif SNAPGFX
  1056.         WriteStr("\n");
  1057.         WriteStr("S-Mail: Mikael Karlsson     | E-Mail: micke@slaka.sirius.se\n");
  1058.         WriteStr("        Lövsättersvägen 10  |         micke@slaka.UUCP\n");
  1059.         WriteStr("        S-585 98  LINKÖPING |         {mxvax|seismo}!sunic!liuida!slaka!micke\n");
  1060.         WriteStr("        Sweden              | Phone:  +46 (0)13 50479\n");
  1061.         goto exitpoint;
  1062.     }
  1063.  
  1064. skipargs:
  1065.     freopen("NIL:", "w", stdout);
  1066.  
  1067.     if (!create) {
  1068.           /* Tell him there are new settings available */
  1069.         Signal(SnapRsrc->Task, SIGBREAKF_CTRL_F);
  1070.         goto exitpoint;
  1071.     }
  1072.  
  1073.     if (!OpenStuff()) {
  1074.         goto close;
  1075.     }
  1076.  
  1077.     textqual = SnapRsrc->textqual;
  1078.     gfxqual = SnapRsrc->gfxqual;
  1079.     insertkey = SnapRsrc->insertkey;
  1080.     cwkey = SnapRsrc->cwkey;
  1081.     TrueUnderscore = SnapRsrc->flags & TRUEUNDERSCORE ? 1 : 0;
  1082. #ifdef SNAPGFX
  1083.     SaveName[0] = '\0';
  1084. #endif
  1085.  
  1086. #ifdef SNAPREXX
  1087.     rexxsignal = upRexxPort("SNAP", &rcl, NULL, &disp);
  1088. #endif SNAPREXX
  1089.  
  1090.     /* This is what we're waiting for */
  1091.     WaitSignal = startsignal | insertsignal | initsignal | cancelsignal |
  1092. #ifdef SNAPREXX
  1093.                  rexxsignal |
  1094. #endif SNAPREXX
  1095.                  cwsignal | SIGBREAKF_CTRL_C | SIGBREAKF_CTRL_F;
  1096.  
  1097.     FOREVER {
  1098.         REGISTER LONGBITS sig;
  1099.  
  1100.         sig = Wait(WaitSignal | timersignal
  1101. #ifdef SNAPGFX
  1102.             | (Sharedport ? (1L << Sharedport->mp_SigBit) : 0L)
  1103. #endif SNAPGFX
  1104.             );
  1105.  
  1106. #ifdef SNAPGFX
  1107.         CheckWindowMsgs();
  1108. #endif SNAPGFX
  1109.  
  1110. #ifdef SNAPREXX
  1111.         if (sig & rexxsignal) {
  1112.             dispRexxPort();
  1113.         }
  1114. #endif SNAPREXX
  1115.         if (sig & SIGBREAKF_CTRL_C) {
  1116.             /* This is my cue. Exit if there are no open windows depending on us */
  1117. #ifdef SNAPGFX
  1118.             if (Sharedrefs) {
  1119.                 DisplayBeep(NULL);
  1120.             } else
  1121. #endif SNAPGFX
  1122.             {
  1123.                 goto close;
  1124.             }
  1125.         }
  1126.         if (sig & SIGBREAKF_CTRL_F) {
  1127.             /* Hey, seems like there are new settings available. */
  1128.             textqual = SnapRsrc->textqual;
  1129.             gfxqual = SnapRsrc->gfxqual;
  1130.             insertkey = SnapRsrc->insertkey;
  1131.             cwkey = SnapRsrc->cwkey;
  1132.             TrueUnderscore = SnapRsrc->flags & TRUEUNDERSCORE ? 1 : 0;
  1133.         }
  1134.         if (sig & initsignal) {
  1135.             if (SnapRsrc->flags & (XEROX | EARLYPATCH)) {
  1136.                 SafePatch();               /* Patch dangerous functions */
  1137.             }
  1138.         }
  1139.         if (sig & cancelsignal) {
  1140.             SafeRestore();
  1141.         }
  1142.         if (sig & startsignal) { /* The handler wants a word in. */
  1143.             SafePatch();
  1144. #ifdef SNAPGFX
  1145.             if (action == snapgfx) {       /* Check user action */
  1146.                 HandleGfx();               /* Get the picture :-) */
  1147.             } else
  1148. #endif SNAPGFX
  1149.             if (action == snaptext && HandleChars()) {  /* Snap some chars */
  1150.                 if (SnapRsrc->flags & XEROX) {
  1151.                     sig |= insertsignal;
  1152.                 }
  1153.             } else {
  1154.                   /* Previous snap wasn't finished when this one started
  1155.                      or this snap failed. */
  1156.                 SetSignal(0L, movesignal | cancelsignal |
  1157.                   donesignal | clicksignal | ticksignal);
  1158.                 DisplayBeep(NULL);
  1159.                 action = noaction;
  1160.             }
  1161.             if (!(sig & insertsignal)) {
  1162.                 SafeRestore();             /* Layers unlocked - all safe */
  1163.             }
  1164.         }
  1165.  
  1166.         if (sig & insertsignal) {
  1167.             LONG i;
  1168.             struct Snap *Snap;
  1169.             ULONG ascii;
  1170.  
  1171.             action = insert;
  1172.             if (Snap = FetchClip()) {  /* Get clipboard data */
  1173.                   /* get the current keymap  */
  1174.                 ConIOR->io_Command =  CD_ASKDEFAULTKEYMAP;
  1175.                 ConIOR->io_Length  = sizeof (struct KeyMap);
  1176.                 ConIOR->io_Data    = (APTR) &keymap;
  1177.                 ConIOR->io_Flags   = 1;    /* no IOQuick   */
  1178.                 DoIO((struct IORequest *)ConIOR);
  1179.                   /* Set up an input request */
  1180.                 inputRequestBlock->io_Command = IND_WRITEEVENT;
  1181.                 inputRequestBlock->io_Flags   = 0L;
  1182.                 inputRequestBlock->io_Length  = (long)sizeof(struct InputEvent);
  1183.                 inputRequestBlock->io_Data    = (APTR)&SimEvent;
  1184.                   /* Translate chars in SnapSpace and insert them
  1185.                      into the input stream. */
  1186.                 insertcount = 0;
  1187.                 ascii = 13;  /* Simulate start of new line */
  1188.                 for (i = 0; Snap->Chars[i] && (action == insert); ++i) {
  1189.                     if (ascii == 13 && modinsert) {
  1190.                         int cnt = 0;
  1191.                         while (ascii = SnapRsrc->Prepend[cnt++]) {
  1192.                             InsertAscii(ascii);
  1193.                         }
  1194.                     }
  1195.  
  1196.                     ascii = Snap->Chars[i];
  1197.                     if (ascii == 10) {
  1198.                         if (modinsert) {
  1199.                             int cnt = 0;
  1200.                             while (ascii = SnapRsrc->Append[cnt++]) {
  1201.                                 InsertAscii(ascii);
  1202.                             }
  1203.                         }
  1204.                         ascii = 13;     /* WYSIWYG? Hah! */
  1205.                     }
  1206.                     InsertAscii(ascii);
  1207.                     if (ascii == 13 && SnapRsrc->linedelay) {
  1208.                         MyTR.tr_node.io_Command = TR_ADDREQUEST;
  1209.                         MyTR.tr_time.tv_micro = SnapRsrc->linedelay;
  1210.                         MyTR.tr_time.tv_secs = 0;
  1211.                         DoIO((struct IORequest *)&MyTR);
  1212.                     }
  1213.                 }
  1214.                 if (modinsert) {
  1215.                     int cnt = 0;
  1216.                     while (ascii = SnapRsrc->Append[cnt++]) {
  1217.                         InsertAscii(ascii);
  1218.                     }
  1219.                 }
  1220.                 SafeRestore();  /* "Depatch" */
  1221.                   /* Free memory given to us by FetchClip() */
  1222.                 FreeMem(Snap, Snap->Size);
  1223.             }
  1224.             action = noaction;
  1225.             modinsert = 0;
  1226.         }
  1227.  
  1228. #ifdef SNAPGFX
  1229.         if (sig & cwsignal) {
  1230.             if (!ControlWindow && !OpenCW()) {
  1231.                 DisplayBeep(NULL);
  1232.             }
  1233.         }
  1234. #endif SNAPGFX
  1235.     }
  1236.  
  1237. close:
  1238. #ifdef SNAPREXX
  1239.     dnRexxPort();
  1240. #endif SNAPREXX
  1241.     CloseStuff();  /* Guess what */
  1242. exitpoint:
  1243.     CloseLibs();
  1244. #ifdef AZTEC_C
  1245.     return 0;
  1246. #endif
  1247. }
  1248.