home *** CD-ROM | disk | FTP | other *** search
/ Mega Top 1 / os2_top1.zip / os2_top1 / APPS / EDITORS / EHP12 / TASTE.C < prev    next >
C/C++ Source or Header  |  1993-10-27  |  26KB  |  654 lines

  1. /****************************************************************/
  2. /*                                                              */
  3. /*      MODUL:  taste.c                                         */
  4. /*                                                              */
  5. /*      FUNKTIONEN:                                             */
  6. /*              - lies_tasten (Tastenbelegunsfile einlesen)     */
  7. /*              - search_next (suche naechsten passenden Bef.)  */
  8. /*              - taste (Tastendruck auswerten)                 */
  9. /*              - newwgetch (Taste von Keyboard || Puffer lesen)*/
  10. /*              - exec_macro (Macro ausfuehren)                 */
  11. /*              - newgetstr (String mittels newgetch einlesen)  */
  12. /*              - get_comstr (Kommandostring einlesen)          */
  13. /*                                                              */
  14. /****************************************************************/
  15.  
  16. #ifdef OS2
  17. #define INCL_DOSSEMAPHORES
  18. #include <os2.h>
  19. #else
  20. #define _ANSI_SOURCE
  21. #endif
  22.  
  23. #include "defs.h"
  24. #include "keys.h"
  25. #include <ctype.h>
  26.  
  27. extern char helpflag;
  28. extern int ks_index;
  29. extern short int *keystack,*e_keystack;  /* puffer-pointer */
  30. extern short int mc_index;
  31. extern WINDOW *status;
  32. extern char clear_buff, /* aus main.c */
  33.         *tasten_inf; /* Name des Tastenbelegungsfiles aus main.c */
  34. extern int do_macro(),do_control(),do_newline(),(*funktion[])();  /* funktionsarray aus auswertung.c f. get_comstr */
  35. extern puff_typ macro[];
  36. #ifdef OS2
  37. extern HMTX sem_handle;
  38. #endif
  39.  
  40. /* *** globale Daten und Initialisierung *** */
  41. static short int eingabe[MAX_COMM_LEN]; /* Bisher eingelesene Zeichen          */
  42. static short int index=0,               /* Index in eingabe                    */
  43.          bef_index=0;           /* aktuelle moegliche Tastenkombination*/
  44. puff_typ  puff_feld[MACRO_NEST_DEPTH];  /* Macropuffer                         */
  45. comm_typ  *comm_feld;                   /* Tastenkombinationen                 */
  46. short int letter,                       /* Buchstabe, falls Befehl T_BUCHSTABE */
  47.       lastcode = -1,                /* Letzte Tastenkombination            */
  48.       newwgetch();
  49.  
  50. #ifndef OWN_CURSES
  51. /*****************************************************************************
  52. *
  53. *  Funktion       Warnton ausgeben (beep)
  54. *  --------
  55. *
  56. *  Beschreibung : Es wird ein CTRL-G ausgegeben, was einen Warnton erzeugt.
  57. *
  58. *****************************************************************************/
  59.  
  60. void beep()
  61. {
  62.    printf("");  /* Beep ausgeben */
  63. }
  64. #endif
  65.  
  66. /*****************************************************************************
  67. *
  68. *  Funktion       Tastenbelegungsfile einlesen (lies_tasten)
  69. *  --------
  70. *
  71. *  Beschreibung : Liest die Tastenbelegungsdatei in das Feld comm_feld ein.
  72. *
  73. *****************************************************************************/
  74.  
  75. void lies_tasten()
  76. {
  77.   /* *** interne Daten *** */
  78.   FILE               *f;     /* Filepointer fuer Tastenbelegungsdatei */
  79.   register short int i,      /* Zaehler fuer Kombinationsnummer       */
  80.              j;      /* Zaehler fuer Indexfeld                */
  81.   register int       n_info; /* Anzahl einzulesender Strings          */
  82.   short int          *index; /* Feld fuer Stringindices               */
  83.   char               *hilf,  /* Zeiger auf Hilfstring                 */
  84.              dummy [256]; /* Zum einlesen der Hilfstring      */
  85.  
  86.   if (!(f = fopen (tasten_inf,"rb"))) /* Tastebelegungsdatei oeffnen */
  87.   {
  88.     print_stat(PROMPT_KEYREAD);
  89.     wart_ret();
  90.     ende(1, TRUE);
  91.   }
  92.   if(fread(&mc_index,sizeof(short int),1,f) < 1) /* Anzahl Kommandos lesen */
  93.   {
  94.     print_stat(PROMPT_KEYLENGTH);
  95.     wart_ret();
  96.     ende(1, TRUE);
  97.   }
  98.   comm_feld = (comm_typ*)  reserve_mem((mc_index+1) * sizeof(comm_typ));
  99.   index     = (short int*) reserve_mem((mc_index+1) * sizeof(short int));
  100.   for (n_info=i=0;i<=mc_index;i++)  /* Alle Kombinationen einlesen */
  101.     if (fread (&comm_feld[i].blen,sizeof(short int),1,f) < 1)
  102.     { /* Laenge der Kombination einlesen hat nicht geklappt */
  103.       print_stat(PROMPT_KEYCOMM);
  104.       wart_ret();
  105.       ende(1, TRUE);
  106.     }
  107.     else /* Laenge Einlesen hat geklappt, dann eigentliche Kombination lesen */
  108.     {
  109.       if (comm_feld[i].blen > MAX_COMM_LEN)
  110.       { /* Befehl seltsamerweise zu lang */
  111.     print_stat(PROMPT_KEYCOMLEN);
  112.     wart_ret();
  113.     ende(1, TRUE);
  114.       }
  115.       fread (comm_feld[i].befehl,sizeof(short int),comm_feld[i].blen,f);
  116.       fread (&index[i],sizeof(short int),1,f); /* Stringindex lesen */
  117.       comm_feld[i].info_text = NULL;
  118.       if(index[i] > -1)
  119.     for (n_info++,j=0;j<i;j++)  /* Testen, ob Stringindex schon in */
  120.       if (index[j] == index[i]) /* Indextabelle enthalten ist      */
  121.       {
  122.         n_info--;   /* Nur einen weiteren String einlesen,  */
  123.         break;      /* falls neuer Index                    */
  124.       }
  125.     }
  126.  
  127.   /* Jetzt die noetige Anzahl Hilfstrings einlesen */
  128.   for (i=0;i<n_info;i++)
  129.   {
  130.     /* Einen String einlesen und testen, ob er mit '\n' terminiert ist */
  131.     if (!fgets (dummy,255,f) || !(hilf = strchr(dummy,'\n')))
  132.     {
  133.       print_stat(PROMPT_KEYHELP);
  134.       wart_ret();
  135.       ende(1, TRUE);
  136.     }
  137.     *hilf = '\0';  /* '\n' ueberschreiben */
  138.     if (!(hilf = save_text (dummy))) /* Hilfstext im Speicher ablegen */
  139.     {
  140.       print_stat(PROMPT_KEYHELPEM);
  141.       wart_ret();
  142.       ende(1, TRUE);
  143.     }
  144.     for (j=0;j<=mc_index;j++) /* Bei allen Tastenkombinationen, die den */
  145.       if (index[j] == i) /* aktuellen Stringindex aufweisen, Zeiger auf */
  146.     comm_feld[j].info_text = hilf; /* Hilfstext setzen              */
  147.   }
  148.   fclose (f);
  149. }
  150.  
  151. /*****************************************************************************
  152. *
  153. *  Funktion       suche naechsten passenden Befehl (search_next)
  154. *  --------
  155. *
  156. *  Parameter    : eingabe   :
  157. *                   Typ          : short int[]
  158. *                   Wertebereich : Pointer auf integer
  159. *                   Bedeutung    : bisher eingelesene Tastencodes
  160. *
  161. *               : index     :
  162. *                   Typ          : short int
  163. *                   Wertebereich : 0..MAX_COMM_LEN
  164. *                   Bedeutung    : index des zuletzt eingelesenen Zeichens
  165. *
  166. *               : bef_index :
  167. *                   Typ          : short int
  168. *                   Wertebereich : 0..mc_index
  169. *                   Bedeutung    : aktuelle, nicht mehr passende Tasten-
  170. *                                  kombination
  171. *
  172. *  Ergebnis     :
  173. *                   Typ          : short int
  174. *                   Wertebereich : -1,1..mc_index
  175. *                   Bedeutung    : naechste passende Tastenkombination
  176. *
  177. *  Beschreibung : Sucht in comm_feld die naechste auf die bisher eingele-
  178. *                 lesenen Zeichen passende Tastenkombination. Wird keine
  179. *                 entsprechende Kombination gefunden, so wird -1 zurueck-
  180. *                 gegeben.
  181. *
  182. *****************************************************************************/
  183.  
  184. short int search_next(eingabe,index,bef_index)
  185. short int eingabe[];
  186. register short int index,bef_index;
  187. {
  188.   /* *** interne Daten *** */
  189.   register short int *inp, /* Zeiger in alte Eingabe            */
  190.              *bef; /* Zeiger in moeglichen "Kandidaten" */
  191.  
  192.   while(++bef_index <= mc_index) /* Alle weiteren Kombinationen testen */
  193.   {
  194.     for(inp = eingabe,bef = comm_feld[bef_index].befehl;
  195.     (inp <=eingabe+index) && *inp == *bef;inp++,bef++);
  196.     if(inp > eingabe + index) /* passende gefunden */
  197.       return(bef_index);
  198.   }
  199.   return(-1);
  200. }
  201.  
  202. /*****************************************************************************
  203. *
  204. *  Funktion       Tastendruck auswerten (taste)
  205. *  --------
  206. *
  207. *  Parameter    :   w
  208. *                   Typ          : WINDOW *
  209. *                   Wertebereich : Pointer auf curses-Windowstruktur
  210. *                   Bedeutung    : Fenster, in dem Befehl eingelesen werden
  211. *                                  soll
  212. *
  213. *  Ergebnis     :
  214. *                   Typ          : short int
  215. *                   Wertebereich : 0..mc_index+1
  216. *                   Bedeutung    : Interne Nummer der Tastenkombination
  217. *
  218. *  Beschreibung : Es wird eine Taste eingelesen und in der Tabelle nach
  219. *                 einer Kombination beginnend mit dieser Taste gesucht.
  220. *                 Wird keine gefunden, so wird mc_index+1 zurueckgegeben und
  221. *                 die Taste in letter gespeichert.
  222. *                 Wird die Kombination mit dieser Taste abgeschlossen, so
  223. *                 wird die Nummer der gefundenen Kombination zurueckgegeben.
  224. *                 Sonst wird das naechste Zeichen gelesen. Ergibt sich da-
  225. *                 durch keine zulaessige Kombination, so werden alle Zeichen
  226. *                 verworfen. Sonst wird wieder verglichen usw.
  227. *                 Ist das Eingabefenster das Statusfenster, so wird der
  228. *                 Cursor nach Anzeige eines Infotextes nicht positioniert.
  229. *
  230. *****************************************************************************/
  231.  
  232. short int taste(w)
  233. WINDOW *w;
  234. {
  235.   /* *** interne Daten und Initialisierung *** */
  236.   short int hilf;        /* Zwischenspeicher fuer letzte Tastenkombination */
  237.   char      hgz = FALSE  /* Flag, ob ein Hilfstext angezeigt wurde         */
  238. #ifdef MOUSE
  239.         , mouse_akt=FALSE  /* Flag, ob Maus aktiviert ist */
  240. #endif
  241.                 ;
  242.  
  243.   if (lastcode != -1)
  244.   {
  245.     hilf = lastcode; /* Falls eine Funktion ein "ungetchar" ausgefuehrt hat, */
  246.     lastcode = -1;   /* wird der geungetcharte code zurueckgegeben.          */
  247.     return (hilf);
  248.   }
  249.   index = bef_index = 0; /* Alle Kombinationen kommen in Frage */
  250.   while(1)
  251.   {
  252. #ifdef MOUSE
  253.     if(!mouse_akt && ks_index == -1 && !index) /* Falls kein Macro aktiv ist: */
  254.     { /* und noch kein Zeichen eingelesen wurde */
  255. #ifdef OS2
  256.       DosReleaseMutexSem (sem_handle);
  257. #else
  258.       set_mouse_int(MOUSE_MASK);  /* Vor Eingabe Maus aktivieren */
  259. #endif
  260.       mouse_akt = TRUE;
  261.       hide_show (MOUSE_SHOW);
  262.     }
  263. #endif
  264.     letter = eingabe[index] = newwgetch(w); /* Ein Zeichen von Tastatur/Macro */
  265. #ifdef MOUSE
  266.     if(mouse_akt)
  267.     { /* Nach erstem gelesenen Zeichen Maus deaktivieren */
  268.       mouse_akt = FALSE; /* damit Maus nicht zwischen ein Kommando funkt */
  269.       hide_show (MOUSE_HIDE);
  270. #ifdef OS2
  271.       DosRequestMutexSem (sem_handle,-1);
  272. #else
  273.       set_mouse_int(0); 
  274. #endif /* OS2 */
  275.     }
  276. #endif /* MOUSE */
  277.     if(hgz)  /* wurde Hilfstext angezeigt? */
  278.     {
  279.       hgz = FALSE;
  280.       clear_stat();                   /* Hilfstext wieder loeschen              */
  281.       if(w != status)                 /* wenn nicht im Statusfenster eingelesen */
  282.     pos_cursor();                 /* wurde, dann muss Cursor wieder positio-*/
  283.     }                                 /* niert werden */
  284.     if (letter == -1)                 /* War nodelay gesetzt und keine Taste    */
  285.       if(!index)                      /* gedrueckt ? Falls erstes Zeichen */
  286.     return (-1);                  /* eine Kombination, dann -1 zurück */
  287.       else                            /* Sonst -1 ignorieren, da sonst evtl. */
  288.     continue;                     /* Kombination "zerhackt" würde */
  289.     if(comm_feld[bef_index].befehl[index] != eingabe[index])
  290.     {
  291.       /* naechsten passenden Befehl suchen */
  292.       if((bef_index = search_next(eingabe,index,bef_index)) < 0) /* keinen gefunden? */
  293.     if(!index && (letter % 256))    /* normal char and not zero */
  294.     {
  295.       index++;                      /* ein zeichen eingelesen */
  296.       return(bef_index = mc_index+1);
  297.     }
  298.     else                            /* Befehl verwerfen */
  299.     {
  300.       index = bef_index = 0;
  301.       continue;
  302.     }
  303.     }
  304.     if(++index == comm_feld[bef_index].blen) /* passte Zeichen, dann testen, */
  305.       return(bef_index);                /* ob komplette Kombination gelesen. */
  306.     if (helpflag && comm_feld[bef_index].info_text)
  307.     { /* wenn Hilfstexte angezeigt werden sollen und die momentane Kom- */
  308.       hgz = TRUE; /* bination einen hat, dann ausgeben */
  309.       print_hilf (comm_feld[bef_index].info_text);
  310.     }
  311.   }
  312. }
  313.  
  314. /*****************************************************************************
  315. *
  316. *  Funktion       Zeichen aus Puffer oder v. Tastatur lesen (newwgetch)
  317. *  --------
  318. *
  319. *  Parameter    : w         :
  320. *                   Typ          : WINDOW *
  321. *                   Wertebereich : Pointer auf curses-Windowstruktur
  322. *                   Bedeutung    : Fenster, in dem eingegeben werden soll
  323. *
  324. *  Ergebnis     :
  325. *                   Typ          : short int
  326. *                   Wertebereich : curses-Tastenwerte
  327. *                   Bedeutung    : aktuelles Zeichen (s.u.)
  328. *
  329. *  Beschreibung : Diese Funktion liefert das naechste aktuelle Zeichen
  330. *                 zurueck. Dies ist, falls noch Zeichen im Puffer sind, d.h.
  331. *                 ks_index noch nicht -1 ist bzw. in Puffer 0 noch nicht das
  332. *                 letzte Zeichen verarbeitet wurde, das aktuelle Zeichen im
  333. *                 Puffer, andernfalls eine eingelesene Taste.
  334. *                 Zur Erklaerung der Puffer:
  335. *                   ks_index ist der Index des aktuellen Puffers. Ist der
  336. *                   Puffer [ks_index] leer und ks_index>0, so wird in
  337. *                   Puffer [ks_index-1] weitergelesen.
  338. *                   Die Puffer sind in einer Tabelle vom Typ puff_typ[]
  339. *                   gespeichert. Das Strukturelement begin stellt einen
  340. *                   Zeiger auf das aktuelle Element dar, waehrend end auf
  341. *                   das Pufferende zeigt.
  342. *                   keystack ist ein Pointer in den aktuellen Puffer und
  343. *                   zeigt auf das aktuelle Element (falls ks_index>=0);
  344. *                   e_keystack zeigt auf das Ende des aktuellen Puffers.
  345. *
  346. *****************************************************************************/
  347.  
  348. short int newwgetch(w)
  349. WINDOW *w;
  350. {
  351.   if(clear_buff) /* Wenn Puffer als zu loeschend markiert sind: */
  352.   {
  353.     while(ks_index > -1)  /* Macro beenden, evtl. freizugebende Strings freigeben */
  354.     {
  355.       if(puff_feld[ks_index].free_flag)
  356.     line_free(puff_feld[ks_index].begin);
  357.       ks_index--;
  358.     }
  359.     clear_buff = FALSE;  /* Flag zuruecksetzen */
  360.   }
  361.   while(ks_index != -1)  /* Wenn ein Puffer aktiv, dann aus Puffer lesen */
  362.   {
  363.     if(keystack && keystack <= e_keystack)    /* noch Zeichen im Puffer? */
  364.       return(*keystack++); /* Dann  aktuelles Pufferzeichen zurueckgeben */
  365.     else       /* Puffer leer */
  366.       if(puff_feld[ks_index].anz_rep) /* War es eine Repeat-Funktion ? */
  367.       {
  368.     puff_feld[ks_index].anz_rep--;
  369.     keystack = puff_feld[ks_index].begin; /* Selben Puffer nochmal */
  370.     e_keystack = puff_feld[ks_index].end;
  371.       }
  372.       else /* Puffer war kein Repeat-Puffer, Puffer loeschen */
  373.       {
  374.     if(puff_feld[ks_index].free_flag)   /* falls free_flag gesetzt ist, Puffer freigeben */
  375.       line_free(puff_feld[ks_index].begin);
  376.     /* keine Zeichen mehr im aktuellen Puffer; vielleicht noch im vorigen? */
  377.     if(--ks_index >= 0)     /* noch nicht erster Puffer? */
  378.     {
  379.       keystack = puff_feld[ks_index].current; /* im vorherigen Puffer weiter */
  380.       e_keystack = puff_feld[ks_index].end;
  381.     }
  382.       }
  383.   }
  384.   /* Kein Puffer (mehr) aktiv, von Tastatur lesen */
  385.   return(wgetch(w));
  386. }
  387.  
  388.  
  389. /*****************************************************************************
  390. *
  391. *  Funktion       Macro ausfuehren (exec_macro)
  392. *  --------
  393. *
  394. *  Parameter    : mnum      :
  395. *                   Typ          : short int
  396. *                   Wertebereich : 'a' - 'a'+ANZ_MACROS
  397. *                   Bedeutung    : Name des auszufuehrenden Macros
  398. *
  399. *  Beschreibung : Der gewuenschte Macro wird ausgefuehrt, indem auf den
  400. *                 Pufferstapel ein neuer Puffer geschoben wird, in den der
  401. *                 Macrotext kopiert wird. Falls das nicht der erste Puffer
  402. *                 auf dem Stapel ist, wird die Position im alten Puffer
  403. *                 in current abgelegt. Anschliessend wird keystack und
  404. *                 ekeystack korrekt gesetzt.
  405. *
  406. *****************************************************************************/
  407.  
  408. void exec_macro(mnum)
  409. register short int mnum;
  410. {
  411.   /* *** interne Daten *** */
  412.   char dummy[80], /* Zum Zusammenflicken der Fehlermeldung */
  413.        old_delay; /* Zwischenspeicher fuer nodelay-Zustand */
  414.  
  415.   if(mnum>='a' && mnum<='z')  /* exec macro */
  416.     if(macro[mnum-='a'].begin) /* Macro auch nicht leer ? */
  417.       if(ks_index < MACRO_NEST_DEPTH - 1) /* Verschachtelungstiefe OK ? */
  418.       {
  419.     if(ks_index >=0) /* falls schon ein Puffer aktiv, aktuelle Position */
  420.       puff_feld[ks_index].current = keystack;       /* im Puffer merken */
  421.  
  422.     /* Zeiger in neuen Puffer setzen */
  423.     keystack = puff_feld[++ks_index].begin = macro[mnum].begin;
  424.     e_keystack = puff_feld[ks_index].end = macro[mnum].end;
  425.     puff_feld[ks_index].anz_rep = 0; /* Puffer ist nicht zu wiederholen */
  426.     puff_feld[ks_index].free_flag = FALSE;  /* Puffer nach Ausfuehrung  */
  427.       } /* nicht freigeben, da sonst Macrotext freigegeben wuerde */
  428.       else /* zu grosse Verschachtelungstiefe */
  429.       {
  430.     clear_buff = TRUE;  /* beim naechsten Aufruf von newwgetch() Puffer loeschen */
  431. #ifdef OWN_CURSES
  432.     if(old_delay = akt_winp->winp->_dlyflag)
  433.       nodelay(akt_winp->winp,FALSE);  /* falls true eingestellt */
  434. #endif
  435.     print_stat(PROMPT_RECURSION);
  436.     wart_ret();
  437.     clear_stat();
  438. #ifdef OWN_CURSES
  439.     nodelay(akt_winp->winp,old_delay);
  440. #endif
  441.       }
  442.     else /* Macro war leer */
  443.     {
  444.       sprintf(dummy,PROMPT_MACROEMPT,mnum+'a');
  445.       print_err(dummy);
  446.     }
  447. }
  448.  
  449. /*****************************************************************************
  450. *
  451. *  Funktion       String von Tastatur einlesen (newgetstr)
  452. *  --------
  453. *
  454. *  Parameter    : w         :
  455. *                   Typ          : WINDOW *
  456. *                   Wertebereich : Pointer auf curses-Windowstruktur
  457. *                   Bedeutung    : Fenster, in dem Text eingelesen werden soll
  458. *
  459. *                 y         :
  460. *                   Typ          : int
  461. *                   Wertebereich : 0 - Anzahl der Zeilen im Window-1
  462. *                   Bedeutung    : Zeile, in der eingelesen werden soll
  463. *
  464. *                 x         :
  465. *                   Typ          : int
  466. *                   Wertebereich : 0 - Anzahl der Spalten im Window-1
  467. *                   Bedeutung    : Spalte, ab der eingelesen werden soll
  468. *
  469. *                 buff      :
  470. *                   Typ          : char *
  471. *                   Wertebereich : Pointer auf Speicherbereich
  472. *                   Bedeutung    : Speicherbereich, in den Eingabe ge-
  473. *                                  schrieben wird (muss min. max_anz + 1
  474. *                                  Bytes lang sein)
  475. *
  476. *                 max_anz   :
  477. *                   Typ          : int
  478. *                   Wertebereich : 0 - MAX_INT
  479. *                   Bedeutung    : Anzahl maximal einzulesender Zeichen
  480. *                                  = 0 : wartet nur auf RETURN
  481. *                 typ       :
  482. *                   Typ          : int
  483. *                   Wertebereich : GS_NUM, GS_ANY
  484. *                   Bedeutung    : GS_NUM: nur Ziffern einlesen
  485. *                                  GS_ANY: alle Zeichen zulassen
  486. *
  487. *  Beschreibung : Diese Funktion liest mittels newgetch einen String ein.
  488. *                 Hierbei sind die Funktionstasten Backspace (loesche Zeichen
  489. *                 links und bewege Cursor um eine Spalte nach links), Pfeil
  490. *                 links (Cursor um eine Position nach links) und Pfeil rechts
  491. *                 (Cursor um eine Position nach rechts) erlaubt. Maximal
  492. *                 koennen max_anz Zeichen eingegeben werden; versucht man,
  493. *                 mehr Zeichen einzugeben, ertoent ein Piepston und die Ein-
  494. *                 gabe wird ignoriert.
  495. *                 Da bei Backspace die Zeile bis zum Ende geloescht wird,
  496. *                 kann unbeabsichtigt Information geloescht werden (s.u.).
  497. *
  498. *****************************************************************************/
  499.  
  500. void newgetstr(w,y,x,buff,max_anz,typ)
  501. WINDOW *w;
  502. int y,x,max_anz,typ;
  503. char *buff;
  504. {
  505.   /* *** interne Daten und Initialisierung *** */
  506.   short int tmp_inp;        /* Zum einlesen eines Zeichens          */
  507.   int       akt_index = 0,  /* Index in Eingabepuffer               */
  508.         max_index = -1; /* Index fuer letztes Zeichen in Puffer */
  509.  
  510.   if(max_anz < 0)
  511.     return;
  512.  
  513.   buff[akt_index] = '\0';  /* Pufferende markieren */
  514.   do
  515.   {
  516.     wmove(w,y,x + akt_index); /* Cursor an gewuenschte Position */
  517.     wrefresh(w);
  518.     switch(tmp_inp = newwgetch(w))    /* echoing has to be disabled */
  519.     {
  520.       case '\010':          /* Backspace */
  521.     if(akt_index > 0)
  522.     { /* Pufferrest eins nach links kopieren */
  523.       fwdcpy(&buff[akt_index-1],&buff[akt_index]);
  524.       akt_index--;
  525.       max_index--;
  526.       mvwaddstr(w,y,x,buff);
  527.       wclrtoeol(w); /* bis Zeilenende loeschen wg. evtl. ESC-codes */
  528.     }
  529.       break;
  530. #ifndef OS2 /* Bei OS/2 ist alles in einem Zeichen enthalten */
  531.       case '\0':            /* "Escape"-Sequenz */
  532.     switch(newwgetch(w))
  533.     {
  534. #endif
  535.       case KEY_LEFT:        /* Pfeil links */
  536.         if(akt_index > 0)
  537.         akt_index--;
  538.         break;
  539.       case KEY_DC:          /* Delete char */
  540.         if(akt_index <= max_index)
  541.         {
  542.           fwdcpy(&buff[akt_index],&buff[akt_index+1]);
  543.           max_index--;
  544.           mvwaddstr(w,y,x,buff);
  545.           wclrtoeol(w); /* bis Zeilenende loeschen wg. evtl. ESC-codes */
  546.         }
  547.         break;
  548.       case KEY_RIGHT:       /* Pfeil rechts */
  549.         if(akt_index <= max_index)
  550.         akt_index++;
  551.         break;
  552. #ifndef OS2
  553.       default:
  554.         beep();  /* Unbekannte "Escape"-Sequenz */
  555.     }
  556.     break;
  557. #endif
  558.       default:
  559.     /* Bei allen anderen Zeichen ausser dem abschliessenden Zeichen   */
  560.     /* Typ testen und falls korrekt und noch Platz im Puffer, Zeichen */
  561.     /* eintragen */
  562.     if(tmp_inp != END_KEY)
  563.       if(max_index < max_anz-1
  564.       && (typ & GS_NUM && isdigit(tmp_inp) || typ & GS_ANY))
  565.       {
  566.         max_index++;
  567.         revcpy(&buff[akt_index+1],&buff[akt_index]);  /* insert char */
  568.         buff[akt_index++] = tmp_inp;
  569.         mvwaddstr(w,y,x,buff);
  570.       }
  571.       else      /* Typ falsch oder Puffer voll */
  572.         beep();
  573.       break;
  574.     }
  575.   } while(tmp_inp != END_KEY);
  576. }
  577.  
  578. /*****************************************************************************
  579. *
  580. *  Funktion       Kommando-String einlesen (get_comstr)
  581. *  --------
  582. *
  583. *  Parameter    : anf       :
  584. *                   Typ          : short int **
  585. *                   Wertebereich : Pointer auf Pointer auf short int
  586. *                   Bedeutung    : Anfang des Kommandostrings
  587. *
  588. *                 end       :
  589. *                   Typ          : short int **
  590. *                   Wertebereich : Pointer auf Pointer auf short int
  591. *                   Bedeutung    : Ende des Kommandostrings
  592. *
  593. *
  594. *  Beschreibung: Es wird ein Kommandostring eingelesen, der mit RETURN ter-
  595. *                miniert sein muss. Die maximale Laenge ist hierbei durch
  596. *                MAX_MACRO_LEN vorgegeben. Anschliessend wird der eingele-
  597. *                sene String mittels reallocmem und memcpy gesichert und
  598. *                in *anf und *end Anfang bzw. Ende des Strings eingetragen.
  599. *                Moechte man in den Kommandostring ein RETURN einfuegen, so
  600. *                kann man dies mittels der Kombination CTRL-c RETURN, ein
  601. *                CTRL-c laesst sicht durch CTRL-c CTRL-c einfuegen.
  602. *                Hat der Eingabestring (ohne RETURN) die Laenge 0, so wird
  603. *                ein NULL-Pointer zurueckgeliefert.
  604. *
  605. ***************************************************************************/
  606.  
  607. void get_comstr(anf,end)
  608. short int **anf,**end;
  609. {
  610.   /* *** interne Daten und Initialisierung *** */
  611.   register short int bef, /* Zum Einlesen einer Tastenkombination     */
  612.              h;   /* Zum Einlesen des Macrozeichens           */
  613.   short int          mbuff[MAX_MACRO_LEN+1];     /* Eingabepuffer     */
  614.   register int       i=0, /* Index in Eingabepuffer mbuff             */
  615.              i2;  /* Zwischenspeicher fuer Index bzgl. Macros */
  616.  
  617.   print_stat(PROMPT_COMMAND);
  618.   while(funktion[bef = taste(status)] != do_newline) /* code fuer newline ist ende */
  619.   {
  620.     if(i + index > MAX_MACRO_LEN) /* Noch Platz ? */
  621.     {
  622.       clear_stat();
  623.       beep();
  624.       pe_or(PROMPT_KEYLONG);
  625.     }
  626.     else                          /* Es war noch Platz */
  627.       if(funktion[bef] == do_control) /* controlcode einfuegen? */
  628.     mbuff[i++] = newwgetch(status); /* dann ein Zeichen lesen und rein */
  629.       else
  630.     if(funktion[bef] == do_macro && i+index+1 < MAX_MACRO_LEN)  /* Macro-Befehl? */
  631.     { /* zuerst Befehl sichern */
  632.       memcpy(&mbuff[i],eingabe,index * sizeof(short int));
  633.       i += index;
  634.       mbuff[i++] = newwgetch(status); /* Macrozeichen lesen und einfuegen */
  635.     }
  636.     else  /* Kein Macrobefehl */
  637.     {     /* Befehlskombination (eingabe) in Puffer kopieren */
  638.       memcpy(&mbuff[i],eingabe,index * sizeof(short int));
  639.       i += index;
  640.     }
  641.     clear_stat();
  642.     print_stat(PROMPT_COMMAND);
  643.   }
  644.   clear_stat();
  645.   if(!i)  /* Eingabelaenge NULL?*/
  646.     *anf = *end = NULL;
  647.   else
  648.   {
  649.     *anf = (short int *)reserve_mem(i * sizeof(short int));
  650.     *end = &(*anf)[i-1];  /* Zeiger auf Anfang und Ende setzen */
  651.     memcpy(*anf,mbuff,i * sizeof(short int)); /* Kommandostring kopieren */
  652.   }
  653. }
  654.