v04i029: GNU Emacs Mouse Editing on tty-5620 - Part 2 of 3

Gernot Heiser heiser at ethz.UUCP
Sat Aug 13 22:30:08 AEST 1988


Posting-number: Volume 4, Issue 29
Submitted-by: "Gernot Heiser" <heiser at ethz.UUCP>
Archive-name: gnumacs-blit/Part2

#! /bin/sh
# This is a shell archive.  Remove anything before this line, then unpack
# it by saving it into a file and typing "sh file".  To overwrite existing
# files, type "sh file -c".  You can also feed this as standard input via
# unshar, or by typing "sh <file", e.g..  If this archive is complete, you
# will see the following message at the end:
#		"End of archive 2 (of 3)."
# Contents:  5620m/5620.c 5620m/5620m.9
# Wrapped by heiser at eiger on Sun Aug  7 14:16:00 1988
PATH=/bin:/usr/bin:/usr/ucb ; export PATH
if test -f '5620m/5620.c' -a "${1}" != "-c" ; then 
  echo shar: Will not clobber existing file \"'5620m/5620.c'\"
else
echo shar: Extracting \"'5620m/5620.c'\" \(17583 characters\)
sed "s/^X//" >'5620m/5620.c' <<'END_OF_FILE'
X/*
X * 5620_mouse - A layers program able to send mouse coordinates but otherwise
X *              behaving like a normal layer
X *
X * Version 2.2
X *
X * Public domain software.
X * Written by Gernot Heiser (heiser at ethz.uucp) in April 1987
X * based on the vt100 terminal emulator by Leif Samuelsson
X *    as modified by Peter Lamb
X * History :
X *   Version 1.3, Gernot Heiser, Stefan Zeiger, July 1987:
X *      selection feedback
X *   Version 1.4, Gernot Heiser, August 1987:
X *      different selection kinds; special ESC-sequence for selection
X *   Version 1.5, Gernot Heiser, September 1987:
X *      define characteristics of layers to clone in startup file
X *      ensure mouse coordinates are sent "as seen"
X *      box cursor when layer is inactive
X *   Version 1.6, Gernot Heiser, September 1987:
X *      scroll bars
X *   Version 1.8, Gernot Heiser, October 1987:
X *      fixed reset bug, set layer size in TERMCAP string, comments (#) in
X *      startup file
X *   Version 1.9, Gernot Heiser, 1988-02-02:
X *      automatically report layer resize,
X *      only clicks left to or on vertical line are in scrollbar
X *   Version 2.0, Gernot Heiser, 1988-02-27:
X *      adapted to mux
X *   Version 2.1, Gernot Heiser, 1988-05-29:
X *      fixed several problems with mux version
X *   Version 2.2, Gernot Heiser, 1988-07-13:
X *      compressed mouse sequences, small fixes
X */
X
X/* 5620 main line */
X
X#include "5620.h"
X
X#define NEED	(KBD|RCV|ALARM|MOUSE)
X#define MAXCLONE    15
X
X       int          cloned            = FALSE;
X       struct tstat clone_info;
X       int          clone_nbr         = 0;
Xstatic char         *gargs [MAXCLONE],
X                    termcap_buf [512],
X                    *general_argv = termcap_buf,
X                    *line_field   = NULL,
X                    *column_field = NULL;
Xstatic char         **gargv[MAXCLONE];
X       int          charwidth;
X       int          charheight;
X
Xstatic
Xvoid clone_main();
X
Xextern
Xvoid clone_0 ()
X{
X   clone_main (0, gargv[0]);
X}
X
Xstatic
Xvoid clone_1 ()
X{
X   clone_main (1, gargv[1]);
X}
X
Xstatic
Xvoid clone_2 ()
X{
X   clone_main (1, gargv[2]);
X}
X
Xstatic
Xvoid clone_3 ()
X{
X   clone_main (1, gargv[3]);
X}
X
Xstatic
Xvoid clone_4 ()
X{
X   clone_main (1, gargv[4]);
X}
X
Xstatic
Xvoid clone_5 ()
X{
X   clone_main (1, gargv[5]);
X}
X
Xstatic
Xvoid clone_6 ()
X{
X   clone_main (1, gargv[6]);
X}
X
Xstatic
Xvoid clone_7 ()
X{
X   clone_main (1, gargv[7]);
X}
X
Xstatic
Xvoid clone_8 ()
X{
X   clone_main (1, gargv[8]);
X}
X
Xstatic
Xvoid clone_9 ()
X{
X   clone_main (1, gargv[9]);
X}
X
Xstatic
Xvoid clone_10 ()
X{
X   clone_main (1, gargv[10]);
X}
X
Xstatic
Xvoid clone_11 ()
X{
X   clone_main (1, gargv[11]);
X}
X
Xstatic
Xvoid clone_12 ()
X{
X   clone_main (1, gargv[12]);
X}
X
Xstatic
Xvoid clone_13 ()
X{
X   clone_main (1, gargv[13]);
X}
X
Xstatic
Xvoid clone_14 ()
X{
X   clone_main (1, gargv[14]);
X}
X
Xstatic void (*clone_func[]) () = {clone_0, clone_1, clone_2, clone_3, clone_4,
X				  clone_5, clone_6, clone_7, clone_8, clone_9,
X				  clone_10, clone_11, clone_12, clone_13,
X				  clone_14};
X
X
Xstatic
Xint get_num (argc, argv, orig, fact, corner, more)
X      register char ***argv;
X      int           *argc, orig, fact;
X      Bool          corner, *more;
X{
X   /* Read a number from the argument string.
X      If the number is prefixed by '+' it is relative to orig,
X      if it is suffixed by 'c' or 'C' it is in character units.
X      Return the absolute number in pixel units.                 */
X
X   int  ch, num = 0;
X   Bool relative = FALSE;
X   
X   if (*more && *argc > 0) {
X      if (relative = ***argv == '+')
X	 (**argv)++;
X      while ((ch = *(**argv)++) >= '0' && ch <= '9') {
X	 num = num * 10 + ch - '0';
X      }
X      if (ch == 'c' || ch == 'C') {
X	 ch = *(**argv)++;
X	 num *= fact;
X	 if (corner)
X	    num += 2 * INSET;  /* all magic as far as I'm concerned */
X      }
X      while (ch == ' ' || ch == '\t')     /* skip whitespace */
X	 ch = *(**argv)++;
X      if (ch == '\0') {  /* end of arg word */
X	 (*argc)--; (*argv)++;
X      }
X      else {
X	 (**argv)--;
X      }
X   }
X   else
X      *more = FALSE;
X   return  relative ? num+orig : num;
X} /* get_num */
X
X
Xstatic
Xchar *get_string (argc, argv, more)
X      register char ***argv;
X      int           *argc;
X      Bool          *more;
X{
X   char ch, *ptr = **argv;
X
X   /* If argument value doesn't start with '-', return a pointer
X      to it, otherwise return NULL.                                   */
X
X   if (*argc <= 0 || *ptr == '-' || !*more) {
X      *more = FALSE;
X      return NULL;
X   }
X   while ((ch = *(**argv)++) != '\0') {
X      if (ch == '\n') {
X	 if (**argv == ptr+1  ||  *(**argv-2) != '\\')
X	    break;
X      }
X   }
X   if (ch == '\n') {
X      *((**argv)-1) = '\0';
X      ch = *(**argv)++;
X   }
X   if (*more = ch != '\0') {
X      (**argv)--;
X   }
X   else {
X      (*argc)--;
X      (*argv)++;
X   }
X   return ptr;
X} /* get_string */
X
X
Xstatic
Xvoid auto_clone (argc, argv, more)
X      register char ***argv;
X      int           *argc;
X      Bool          *more;
X{
X   Rectangle   r;
X   struct Proc *p;
X   char        *ptr;
X
X   if (*argc > 0) {
X      *more = TRUE;
X      while (***argv == ' '  || ***argv == '\t')  /* skip white space */
X	 (**argv)++;
X      if (***argv == '#') {  /* comment line - ignore */
X	 while (***argv != '\n'  &&  ***argv != '\0') {
X	    (**argv)++;
X	 }
X	 if (***argv == '\n') {
X	    (**argv)++;
X	 }
X	 if (***argv == '\0') {
X	    (*argc)--; (*argv)++;
X	 }
X	 return;
X      }
X   }
X   else {
X      *more = FALSE;
X      return;
X   }
X   r.origin.x = get_num (argc, argv, J_BORDER, charwidth, FALSE, more);
X   r.origin.y = get_num (argc, argv, J_BORDER, charheight, FALSE, more);
X   r.corner.x = get_num (argc, argv, r.origin.x, charwidth, TRUE, more);
X   r.corner.y = get_num (argc, argv, r.origin.y, charheight, TRUE, more);
X   ptr = get_string (argc, argv, more);
X   if (++clone_nbr > MAXCLONE)
X      return;
X   *(gargv [clone_nbr] = &gargs [clone_nbr]) = ptr;
X
X      /* attempt to move rectangle into "valid region": */
X   r = rsubp (r, Pt (r.corner.x <= XMAX-J_BORDER
X		                            ? 0 : r.corner.x+J_BORDER-XMAX,
X		     r.corner.y <= YMAX-J_BORDER
X		                            ? 0 : r.corner.y+J_BORDER-YMAX));
X   r = raddp (r, Pt (r.origin.x >= J_BORDER ? 0 : J_BORDER-r.origin.x,
X		     r.origin.y >= J_BORDER ? 0 : J_BORDER-r.origin.y));
X      /* clip rectangle to "valid region": */
X   if (!rectclip (&r, inset (Rect (0, 0, XMAX, YMAX), J_BORDER))  ||
X       r.corner.x - r.origin.x < XMIN  ||  r.corner.y - r.origin.y < YMIN) {
X      return;    /* illegal rectangle */
X   }
X
X#ifdef DEBUG
X   sendnchars (15, "echo cloning '(");
X   send_num (r.origin.x); sendchar (',');
X   send_num (r.origin.y); sendchar (',');
X   send_num (r.corner.x); sendchar (',');
X   send_num (r.corner.y); send_string (")' '");
X   send_string (*gargv); send_string ("'\n");
X#endif
X
X   if (p = newproc (clone_func [clone_nbr])) {
X      if (p->layer = newlayer (inset (r, - BORDER))) {
X	    /* the parameter to "newlayer" will determine */
X	    /* the size of the outer rectangle */
X	 p->rect = inset (r, BORDER);  /* this rectangle will be */
X				       /* reported by jwin       */
X#ifdef MUX
X	 muxnewwind (p, C_NEW);
X#else
X	 mpxnewwind (p, C_NEW);
X#endif
X         tolayer (p->layer);
X      }
X      else {
X	 p->state = 0;
X	 return;
X      }
X   }
X   else {
X      return;
X   }
X} /* auto_clone */
X
X
Xstatic
Xvoid send_arg (argv, newline)
X      char *argv;
X      Bool newline;
X{
X   int l;
X
X   if (argv && (l = strlen (argv))) {
X      sendnchars (l, argv);
X      if (newline) {
X	 sendchar ('\n');
X      }
X   }
X} /* send_arg */
X
X
Xstatic
Xchar *put_str (buffer, str)
X      char *buffer, *str;
X{
X   while (*str != '\0') {
X      *buffer++ = *str++;
X   }
X   return  buffer;
X}
X
X
Xstatic
Xchar *put_nbr (buffer, nbr)
X      char *buffer;
X      int  nbr;
X{
X   *buffer++ = nbr/10 + '0';
X   *buffer++ = nbr%10 + '0';
X   return  buffer;
X}
X
X
Xstatic
Xvoid term_main(t, argc, argv)
X      register struct tstat *t;
X      char **argv;
X{
X   if (line_field != NULL) {
X      put_nbr (line_field, nrows);
X      put_nbr (column_field, ncols);
X   }
X#ifndef MUX
X   send_arg (general_argv, TRUE);
X#endif
X   while(argc > 0) {
X      send_arg (*argv++, TRUE);
X      argc--;
X   }
X
X   tock = FALSE;
X   peek_ch     = -1;     /* init input buffer */
X   select_kind =  0;     /* init selection kind */
X   cancel      = FALSE;
X   request(NEED);
X   
X   for(;;) {
X      handle_output(t);  /* handle_input() called from wreceive() */
X   }
X} /* term_main */
X
X
Xvoid main(argc, argv)
X      int  argc;
X      char **argv;
X{
X   register struct tstat *t = (struct tstat *)alloc(sizeof (struct tstat));
X   Bool     more, was_current;
X   Layer    *my_layer;
X
X   if(t == 0)
X      exit();
X
X   init_term(t);
X   do_reset(t);
X   my_layer = P->layer;
X   was_current = own () & MOUSE;
X
X   argc--; argv++;
X   while(argc > 0 && **argv == '-') {
X      switch(argv[0][1]) {
X       case 'a':
X	 argc--; argv++;
X	 if (argc > 0) {
X	    while (**argv != '\0') {
X	       if (**argv     == '#'  &&  *(*argv+1) == '#'  &&
X		   *(*argv+2) == '#'  &&  *(*argv+3) == '#'    )  {
X		  general_argv = put_str (general_argv, "li#00:co#00");
X		  line_field   = general_argv - 8; /* line field */
X		  column_field = general_argv - 2; /* column field */
X		  general_argv = put_str (general_argv, *argv+4);
X		  break;
X	       }
X	       else {
X		  *general_argv++ = *(*argv)++;
X	       }
X	    }
X	    *general_argv = '\0';
X	    general_argv  = termcap_buf;
X	    argc--; argv++;
X	 }
X	 break;
X       case 'c':
X	 argc--; argv++;
X	 do auto_clone (&argc, &argv, &more);
X	    while (more);
X	 break;
X       default:
X	 argc--; argv++;
X	 break;
X      }
X   }
X#if FALSE
X   if (was_current) {
X      upfront (my_layer);  /* bring "original" layer on top */
X      tolayer (my_layer);  /* make it current again */
X   }
X#endif FALSE
X   term_main (t, argc, argv);
X} /* main */
X
X
Xstatic
Xvoid clone_main(argc, argv)
X      int  argc;
X      char **argv;
X{
X	register struct tstat *t = (struct tstat *)alloc(sizeof(struct tstat));
X
X	*t = clone_info;		/* Get config data out of shared bss */
X
X	if((P->data = alloc(sizeof(struct udata))) == 0) {
X	   exit();
X	}
X
X	P->state |= USER;
X
X	cloned = TRUE;
X
X	init_term(t);
X	do_reset(t);
X
X#ifdef MUX
X        send_arg (general_argv, TRUE);
X#endif
X	term_main(t, argc, argv);
X} /* clone_main */
X
X
Xstatic
Xvoid handle_input(t)
Xregister struct tstat *t;
X{
X   int k;
X   static char trans [] = "WTXUYV";
X
X   while((k = kbdchar()) >= 0)
X      if (!kbd_lock) {
X#ifdef MUX
X         if (k < 0200) {                    /* "normal" keyboard key */
X            sendchar(k);
X            return;
X         }
X         else if (k < 0300) {               /* spec. +  shifted keypad: SS3 */
X            sendnchars (2, "\033O");
X            sendchar (0220 <= k && k <= 0231 ? k-040  : /* shifted keypad */
X                      0232 <= k && k <= 0233 ? k-055  : /* keypad - . */
X                      k == 0200              ? 'k'    : /* BRK */
X                      k == 0256              ? 'l'    : /* SETUP */
X                      k == 0262              ? 'o'    : /* NUM LOCK */
X                                               '\033'); /* no such key */
X         }
X         else if (0310 <= k && k <= 0317) { /* shifted functions keys: CSI */
X            sendnchars (3, "\033[2");
X            sendchar (k-0227); /* decimal function key nbr */
X            sendchar ('~');
X         }
X         else if (0350 <= k && k <= 0357) { /* unshifted functions keys: CSI */
X            sendnchars (3, "\033[1");
X            sendchar (k-0267); /* decimal function key nbr */
X            sendchar ('~');
X         }
X         else if (k == 0345) {
X            sendnchars (4, "\033[2J");      /* CLEAR */
X         }
X         else {                             /* others: CSI */
X            sendnchars (2, "\033[");
X            sendchar (k == 0300              ? 'H'    : /* HOME */
X                      k <= 0306              ? k-0200 : /* cursor keys */
X                      0322 <= k && k <= 0327 ? trans [k-0322] : /* 4-9 */
X                      k == 0365              ? 'Z'    : /* shift CLEAR */
X                                               '\033'); /* no such key */
X         }
X         if (! open_mode) { /* if not open mode append newline */
X            sendchar ('\n');
X         }
X#else
X         sendchar(k);
X#endif
X      }
X      else
X         ringbell();
X} /* handle_input */
X
X
Xextern
Xvoid setrect(t, r)
Xregister struct tstat *t;
XRectangle r;
X{
X   Srect = inset(r, BORDER);
X   Trect = Srect;
X   if (scroll_active)
X      Trect.origin.x = Srect.origin.x + charwidth +
X	               (Srect.corner.x - Srect.origin.x) % charwidth;
X} /* setrect */
X
X
Xint wreceive(t)
Xregister struct tstat *t;
X{
X	int got;
X	int atime = 1;
X	register ch = peek_ch;
X	void term_mouse ();
X        void reshape ();
X
X	peek_ch = -1;
X	alarm(1);
X	for(;;) {
X	        if (ch > 0)
X		   return (ch);
X		got = wait(NEED);
X		if(P->state & MOVED) {
X			setrect(t, D_rect);
X			P->state &= ~MOVED;
X		} else if(P->state & RESHAPED) {
X			reshape(t,TRUE);
X		}
X		if(got & KBD)
X			handle_input(t);
X		if(got & ALARM) {
X			cursor_on(t);
X			tock = !tock;
X			alarm(30 - realtime() % 30);
X		}
X		if(got & MOUSE) {
X			term_mouse(t);
X		}
X		if(got & RCV)
X			return rcvchar(t);
X	}
X} /* wreceive */
X
X
X#undef transform
X#define transform(x) if      (sel_but == 1)  x  = (x&6) >> 1;            \
X                     else if (sel_but == 2)  x  = x & 1  |  (x&4) >> 1;  \
X		     else                    x &= 3;                     \
X		     if (del_but < copy_but) x  = (x >> 1) | (x << 1) & 3
Xstatic
Xint inv_kind (t, old_buts, buts, kind)
X      register struct tstat *t;
X      int old_buts, buts, *kind;
X{
X   int inv, old = *kind - select;
X
X   transform (old_buts);  /* make "copy-bit" first, "delete-bit" second */
X   transform (buts);
X     /* the following looks like magic but is just boolean algebra */
X   *kind  = old == buts  ?  0  :  old_buts | buts;
X   inv    = old ^ *kind;
X   *kind += select;
X   return   inv + select + 3;  /* + 3 for inverse pattern */
X}
X#undef transform
X
X
X#define rowof(ry)	  ((ry - Trect.origin.y) / charheight)
X#define colof(cx)	  ((cx - Trect.origin.x) / charwidth)
X
X#define in_scrollbar(xy)  (xy.x < Trect.origin.x - BORDER)
X
Xstatic
Xvoid term_mouse(t)
X      register struct tstat *t;
X{
X   int   buts;
X   Bool  scrolling;
X   Point mouse_xy;
X
X   if (!mouse_active) {
X      if (r_butt()) {             /* do layers menu */
X         while (r_butt());
X       }
X      else if (m_butt()) {        /* do own menu */
X         do_menu (t, 2);
X       }
X      else if (l_butt()) {        /* wait till button released */
X         request (NEED & ~MOUSE);
X         wait (CPU);
X         request (NEED);
X       }
X      if(mcursr >= 0) {
X         mcursor_off(t);
X       }
X      return;
X   }
X
X   if ((buts = any_butt()) || mbuts) {  /* update mouse cursor */
X      cancel |= !ptinrect (mouse_xy=Mouse.xy, P->layer->rect) | !is_current;
X      mrow = rowof (mouse_xy.y);
X      mrow = mrow < 0  ?  0  :  mrow >= nrows  ?  nrows-1  :  mrow;
X      scrolling = in_scrollbar (mouse_xy);
X      if (mbuts && !select_kind ||     /* point event, not a selection */
X	  !mbuts && (scrolling || !(buts & sel_but))) {
X	 mcol = colof(mouse_xy.x);      /* point "to" char */
X	 mcol = scrolling  ?  -1
X	                   :  mcol < 0  ?  0
X			                :  mcol >= ncols  ?  ncols-1
X					                  :  mcol;
X         if (!mbuts) { /* just started pointing */
X            tot_buts = buts;
X            mrow_0 = mrow;
X            mcol_0 = mcol;
X         }
X         else if (!buts) { /* just finished pointing */
X            if (!cancel) {
X               send_region (t, mrow_0, mcol_0, mrow_old, mcol_old,
X                            tot_buts, FALSE);
X               tot_buts = 0;
X            }
X            cancel   = FALSE;
X         }
X         else {
X            tot_buts |= buts;
X         }
X      } /* point event */
X
X      else {             /* selection */
X	 mcol = colof(mouse_xy.x + charwidth/2);   /* point "between" chars */
X	 mcol = mcol < 0  ?  0  :  mcol >= ncols  ?  ncols  :  mcol;
X	 if (!mbuts) {               /* start selection */
X	    mrow_0 = mrow;
X	    mcol_0 = mcol;
X	    select_kind = buts & copy_but ? (buts & del_but ? move : copy)
X	                                  :  buts & del_but ? delete : select;
X	 }
X	 else {          /* already selecting */
X	    if (!buts) {           /* end selection */
X	       hilight_region (t, mrow_0, mcol_0, mrow_old, mcol_old,
X			       select_kind);
X	       if (!cancel)
X		  send_region (t, mrow_0, mcol_0, mrow_old, mcol_old,
X			       select_kind, TRUE);
X	       cancel      = FALSE;
X	       select_kind = 0;
X	    }
X	    else if (buts & ~mbuts & ~sel_but) {   /* add button */
X	       hilight_region (t, mrow_0, mcol_0, mrow_old, mcol_old,
X			       inv_kind (t, mbuts, buts, &select_kind));
X	    }
X	    hilight_region (t, mrow_old, mcol_old, mrow, mcol, select_kind);
X	 }  /* already selecting */
X      } /* selection */
X      mbuts = buts;
X      mrow_old = mrow;
X      mcol_old = mcol;
X      cursor_on (t);
X   } /* buts || mbuts */
X} /* term_mouse */
X
X
Xvoid reshape(t, notify)
Xregister struct tstat *t;
XBool notify;
X{
X   int old_nrows = nrows;
X   int old_ncols = ncols;
X   P->state     &= ~RESHAPED;
X   P->rect       = inset (P->layer->rect, INSET);
X   D_rect        = P->rect;
X   setrect (t, D_rect);
X   ncols         = (Trect.corner.x - Trect.origin.x) / charwidth;
X   nrows         = (Trect.corner.y - Trect.origin.y) / charheight;
X   top_margin    = 1;
X   bottom_margin = nrows;
X   if (! notify  ||  ncols != old_ncols  ||  nrows != old_nrows) {
X      row   = 1;
X      col   = 1;
X      if (notify) {
X         send_reshaped (t);
X      }
X      clear_screen (t);
X   }
X} /* reshape */
END_OF_FILE
if test 17583 -ne `wc -c <'5620m/5620.c'`; then
    echo shar: \"'5620m/5620.c'\" unpacked with wrong size!
fi
# end of '5620m/5620.c'
fi
if test -f '5620m/5620m.9' -a "${1}" != "-c" ; then 
  echo shar: Will not clobber existing file \"'5620m/5620m.9'\"
else
echo shar: Extracting \"'5620m/5620m.9'\" \(17932 characters\)
sed "s/^X//" >'5620m/5620m.9' <<'END_OF_FILE'
X.de sh
X.br
X.ne 5
X.PP
X\fB\\$1\fR
X.PP
X..
X.ds ZZ CORE PACKAGE
X.TH 5620M 9 DMD local
X.SH NAME
X5620m, 5620mtset, 5620mstty
X\- 5620 terminal emulator to support mouse editing with \f2emacs\f1.
X.SH SYNOPSIS
X.B 5620m
X[
X.B \-f
Xfile ]
X[ command ... ]
X.PP
Xeval
X.B `5620mtset [options]`
X.PP
X.B 5620mstty
X.SH DESCRIPTION
XThe
X.I 5620_mouse
Xutility
Xis an interactive terminal emulation program that runs under
X.IR mux (9)
Xon a DMD 5620 terminal.
X.I 5620mtset
Xis used to inquire the layer size and set up the terminal environment
Xaccordingly.
X.I 5620mstty
Xis used by the -f option of 5620mtset and does not need to be called
Xexplicitly by the user.
X.PP
X.I 5620_mouse
Xsupports almost all features of a `normal' layer but in addition is capable
Xof sending mouse coordinates to the Unix process. Editors like
X.IR emacs (1)
Xcan interpret the received mouse information to allow advanced mouse editing.
XAdditional display capabilities make editing faster even without using the
Xmouse, provided the editor can use the appropriate
X.IR termcap (5)
Xentries.
X.sh "Command line arguments"
XThere are two kinds of command line arguments:
X.TP 12
X\fB\-f\fP \fIfile\^\fP
XCreate new layers as specified in the named
X.IR file ,
Xall running the
X.B 5620_mouse
Xterminal emulator.
XThe syntax and semantics  of the file is similiar, but not quite identical, to
Xthe corresponding file of the
X.IR layers (1)
Xcommand.
XEach line of the file represents one new layer.  It contains the rectangle
Xcoordinates ordered, origin.x, origin.y, corner.x, corner.y, followed by
Xthe command(s) to be executed in the layer.  The separators are space or tab.
XLines whose first non-whitespace character is `#' are treated as comments.
XLines can be continued by quoting the
Xend-of-line with a backslash (`\\').
XThe screen is {8, 8, 792, 1016}.  
XThis enforces the same 8 pixel border
Xthat making layers with the mouse does.  Layers which are not fully contained
Xwithin the border will be moved inside or clipped.
X.br
XThe rectangle may be specified using absolute or relative coordinates in pixel
Xor character units. A number prefixed by `+' is relative (to origin for the
Xcorner, to (8,8) for the origin), absolute otherwise. A number suffixed by `c'
Xor `C' is in character units, pixel units otherwise.
X.TP
Xcommand ...
Xis fed to the shell running in the parent layer after the program has been
Xdownloaded and the TERMCAP environment variable has been set. Note that since a
Xsubshell is spawned in the layer, typing `5620_mouse;command ...'. would not
Xexecute `command' until the subshell exits. Since the subshell in general will
Xnot exit until the layer is destroyed, `command' may never be executed.
X.TP
X	
XOther options are recognised but are for internal purposes and should not
Xbe used.
X.sh "Terminal modes"
XThe emulator operates in two different modes: \fInormal\fR and \fIopen\fR mode.
XIn \fInormal\fR mode, the function of the right and left mouse buttons is
Xidentical to a `normal' layer. The middle button shows an additional menu which
Xallows for the following selections:
X.TP 10
X\fBclone\fR
XSimiliar to the \fImux\fR menu \fBNew\fR but the newly created layer runs
X\fI5620m\fR. 
X.TP
X\fBinvert\fR
XToggles the layer display between normal and inverse video.
X.TP
X\fBreset\fR
XResets the emulator to its default state.
X.TP
X\fBexit\fR
XExits the terminal emulator in the layer reverting to \fImux\fR's default
Xemulator.
X.PP
X`Open' mode provides special editing support. It is entered and exited upon
Xreceipt of certain escape sequences (see \fBReceived codes\fR below).
XThe behaviour of the terminal
Xin `open' mode is governed by two flags that can also be set or unset by escape
Xsequences. If neither of the flags are set, the only difference to `normal'
Xmode is that the mouse buttons are ignored and hence no menus are available.
X.PP
XIf the flag \fImouse_en\fR is set, mouse coordinates are sent to the host. This
Xcan be used by an editor like 
X.IR emacs (1)
Xto support editing operations like cursor positioning and text selection.
XWhenever mouse buttons are pressed and released, a \fBmouse event\fR is
Xreported in form of an escape sequence describing the initial and final mouse
Xcoordinates and the depressed buttons.
X.PP
XIn addition, buttons can be given special meanings. A \fBselection button\fR,
Xwhen pressed, will receive special treatment. The text
Xswept with the mouse while the selection button is depressed is highlighted on
Xthe screen. Once the button is released, the highlighting is reversed and the
Xstarting and ending points of the selection are reported to the host as a
X\fBselection event\fR.
XNote that a selection event is generated only if the selection button is the
Xfirst one to be pressed.
X.PP
XA further button can be given the special meaning of \fBcopy button\fR, which
Ximplicitly defines the remaining button to be the \fBdelete button\fR. When
Xpressing the copy button during a selection, it becomes a `copy selection';
Xpressing the delete button generates a `delete selection' and pressing all
Xbuttons leads to a `move selection'. Releasing and re-pressing the
Xcorresponding button converts the selection back to a `plain selection' and so
Xon.
X.PP
XThe selection kind is indicated by different patterns for highlighting the
Xselected text: while the contents of a `plain selection' are uniformly
Xdisplayed in inverse video, a `copy selection' has a ragged top, a `delete
Xselection' a ragged bottom, and a `move selection' has both.
X.PP
XThe names of the selection kinds imply a certain meaning of the various
Xbutton combinations. The terminal, however, does not actually perform any
Xcopying or deleting, this is left to the editor. All the terminal does is to
Xprovide 
Xthe user with a visual feedback of what he/she is doing and to report
Xthe user's intent to the
Xhost system.
X.PP
XThe second flag is \fIscroll_en\fR. When it is set in `open mode', a scroll bar
Xis drawn along the left side of the layer. Pressing a mouse button in the
Xscroll bar is reported as a mouse event, even if the pressed button is the
X`select button'. The editor running on the host system can recognize scroll
Xevents due to their x-coordinate being zero.
XNote that with the scroll bar the usable display area is reduced by one column,
Xthe editor must account for that.
X.sh "Received codes"
X.DT
X.nf
X	\fISequence\fR	\fITermcap\fR		\fIFunction\fR
X	ESC [ H		kh=\\E[H		Cursor Home\(dg
X			ho=\\E[H
X	ESC [ 70;1 H	kH=\\E[70H		Cursor Home Down
X			ll=\\E[70H
X	ESC [ l;c H	cm=\\E[%i%d;%dH	Cursor Positioning\(dg
X	ESC [ n A	ku=\\E[A		Cursor Up\(dd
X			up=\\E[A
X	ESC [ n B	kd=\\E[B		Cursor Down\(dd
X	ESC [ n C	kr=\\E[C		Cursor Right\(dd
X			nd=\\E[C
X	ESC [ n D	kl=\\E[D		Cursor Left\(dd
X	ESC [ J		cd=\\E[J		Clear to End of Screen\(dg
X	ESC [ 1 J	???			Clear to Beginning of Screen\(dg
X	ESC [ 2 J	kC=\\E[2J		Cursor Home and Clear Screen\(dg
X	ESC [ K	ce=\\E[K		Clear to End of Line\(dg
X	ESC [ 1 K	???			Clear to Beginning of Line\(dg
X	ESC [ from;to r	cs=\\E[%i%d;%dr	Define Scrolling Region
X	ESC [ n S	SF=\\E%dS		Scroll Up\(dg
X			sf=\\ES
X	ESC [ n S	SR=\\E%dT		Scroll Down\(dg
X			sr=\\ET
X	ESC [ R c n R	rp=\\E[R%.%dR	Repeat Character
X	ESC [ n @	IC=\\E%d@		Insert Characters\(dg\(dg
X			ic=\\E@
X	ESC [ n P	DC=\\E%dP		Delete Characters\(dg\(dg
X			dc=\\EP
X	ESC [ n L	AL=\\E%dL		Insert Lines\(dg\(dg
X			al=\\EL
X	ESC [ n M	DL=\\E%dM		Delete Lines\(dg\(dg
X			dl=\\EM
X	ESC [ 4 m	us=\\E4m		Start Underline\(dg\(dg
X	ESC [ 7 m	so=\\E7m		Start Highlight\(dg\(dg
X			mr=\\E7m
X	ESC [ 0m	ue=\\E0m		End Underline/Highlight\(dg\(dg
X			se=\\E0m
X			me=\\E0m
X	ESC [ ? n h	vs=\\E[?h		Enter Open Mode
X	ESC [ ? n l	ve=\\E[?l		Exit Open Mode
X	ESC [ ? n m				Enable/Disable Mouse
X	ESC [ ? n s				Enable/Disable Scroll Bar
X	ESC [ ? m;s;c b				Define Mouse Buttons
X	ESC 7		sc=\\E7			Save Cursor Position\(dg
X	ESC 8		rc=\\E8			Restore Cursor Position\(dg
X	ESC [ c					Send Terminal Id
X	ESC z					Send Terminal Id
X	ESC [ ? C				Send Window Size
X	ESC c		rs=\\Ec			Reset Terminal
X.fi
X.TP 5
X\(dg
XThis feature is described in the 5620 Owner's Manual and is not discussed here.
X.TP
X\(dd
XThis feature is similiar to the one described in the 5620 Owner's Manual. The
Xoptional parameter gives the repeat count of the operation.
X.TP
X\(dg\(dg
XThis feature is supported by `normal' layers on DMDs with new ROMs.
X.PP
X\fBEffect of receiving these sequences:\fB
X.TP 20
X\fBCursor Home Down\fR
Xmoves the cursor to the first column in the last line of the layer.
X.TP
X\fBDefine Scrolling Region\fR
Xdefines future scrolling operations to be restricted to lines \fIfrom\fR to
X\fIto\fR inclusive. Default is 1 for \fIfrom\fR and the last line for \fIto\fR.
X.TP
X\fBRepeat Character\fR
Xwrite character \fIc\fR \fIn\fR times, same as sending \fIc\fR \fIn\fR times.
X.TP
X\fBInsert Characters\fR
Xinsert \fIn\fR (default 1) spaces by shifting the characters to the right of
Xthe cursor \fIn\fR positions to the right. Characters shifted bejond the
Xrightmost column are lost.
X.TP
X\fBDelete Characters\fR
Xdelete \fIn\fR (default 1) characters by shifting characters \fIn\fR positions
Xto the left, starting \fIn\fR positions to the right of the cursor. The
Xfirst \fIn\fR characters to the right of the cursor are lost.
X.TP
X\fBInsert Lines\fR
Xinsert \fIn\fR (default 1) empty lines starting at the line with the cursor.
XLines displayed below the cursor move down. Lines moved past the bottom of the
Xlayer (or the bottom margin set by a \fIDefine Scrolling Region\fR sequence)
Xare lost. 
X.TP
X\fBDelete Lines\fR
Xdelete \fIn\fR (default 1) lines starting at the line with the cursor. As lines
Xare deleted, lines below the cursor move up.
X.TP
X\fBStart Underline\fR
Xunderline characters displayed in the future.
X.TP
X\fBStart Highlight\fR
Xhighlight future characters by displaying them in inverse video.
X.TP
X\fBEnd Underline/Highlight\fR
Xdisplay future characters without underlining or highlighting.
X.TP
X\fBEnter Open Mode\fR
Xdisable `normal' layers operation of mouse buttons. If the mouse has been
Xenabled, send \fIReport Mouse Event\fR or \fIReport Selection\fR sequences when
Xmouse buttons are pressed or released. If the scroll bar has been enabled, shift
Xthe whole display one column to the right and draw the scroll bar. \fIN\fR is
Xignored. 
X.TP
X\fBExit Open Mode\fR
Xreturn to `normal' layers operation of mouse buttons. If the scroll bar has been
Xenabled, shift the whole display back to the left, removing the
Xscroll bar. \fIN\fR is ignored. 
X.TP
X\fBEnable/Disable Mouse\fR
Xset the flag \fImouse_en\fR if \fIn\fR (default 0) is not equal to 0, otherwise
Xreset the flag. If in `open mode' start sending mouse reports iff
X\fImouse_en\fR is set.
X.TP
X\fBEnable/Disable Scroll Bar\fR
Xset the flag \fIscroll_en\fR if \fIn\fR (default 0) is not equal to 0, otherwise
Xreset the flag. If in `open mode' draw the scroll bar if \fIscroll_en\fR is set,
Xremove the scroll bar if not set.
X.TP
X\fBDefine Mouse Buttons\fR
Xset the \fIselection button\fR to \fIs\fR, the \fIcopy button\fR to \fIc\fR.
X\fIm\fR is currently ignored. Buttons are specified as 1, 2 or 4, meaning the
Xright, middle or left button respectively. Unspecified parameters default to 0,
Xinitial setting is all zeros.  A \fIselection button\fR of 0 disables
Xselections. A \fIcopy button\fR of 0 (with the \fIselection button\fR being
Xnon-zero) disables selection kinds.
X.TP
X\fBSend Terminal Id\fR
Xas defined in the DMD manual but the response is different (see \fIReport
XTerminal Type\fR
Xcode below).
X.TP
X\fBSend Window Size\fR
Xreply with a \fIReport Window Size\fR sequence.
X.TP
X\fBReset Terminal\fR
Xclear the screen and move the cursor to home position. All flags are reset to
Xtheir initial values. In particular \fImouse_en\fR, \fIscroll_en\fR are reset,
X\fIselection button\fR and \fIcopy button\fR are set to zero and the emulator
Xis put into `normal mode'. This action is identical to selection of the
X\fIreset\fR menu on the middle button.
X.PP
XOther useful
X.IR termcap (7)
Xentries are:
X.br
Xam:bs:pt:im=:ei=:dm=:ed=:do=^J:kb=^H:le=^H:ms:
X.br
XThe full terminal capablities of a 5620m layer is reflected by the \fI5620x\fR
Xentry in \fI/etc/termcap\fR.
X.sh "Special key codes"
XThe following table gives the codes transmitted to the host upon pressing the
Xindicated keys on the keyboard. `Code 1' is transmitted if the key is pressed
Xby itself, `Code 2' is transmitted if the \fISHIFT\fR or \fICTRL\fR key is
Xpressed at the same time. Note that `.', `-' and `0' to `9' in the table refer
Xto keys on the numeric keypad only.
X
X.DT
X.nf
X	\fIkey\fR		\fICode 1\fR		\fICode 2\fR
X	-		ESC [ D		ESC O m
X	0		ESC [ C		ESC O p
X	.		ESC [ B		ESC O n
X	1		ESC [ H		ESC O q
X	2		ESC [ A		ESC O r
X	3		ESC [ F		ESC O s
X	4		ESC [ T		ESC O t
X	5		ESC [ U		ESC O u
X	6		ESC [ V		ESC O v
X	7		ESC [ W	ESC O w
X	8		ESC [ X		ESC O x
X	9		ESC [ Y		ESC O y
X	CLEAR		ESC [ 2 J	ESC [ Z
X	SET UP	ESC O l	\fIfreeze mux\fR
X	BRK		ESC O k	\fIdisconnect\fR
X
X	NUM LOCK	ESC O o	ESC O o
X
X	f1		ESC [ 1 1 ~	ESC [ 2 1 ~
X	f2		ESC [ 1 2 ~	ESC [ 2 2 ~
X	f3		ESC [ 1 3 ~	ESC [ 2 3 ~
X	f4		ESC [ 1 4 ~	ESC [ 2 4 ~
X	f5		ESC [ 1 5 ~	ESC [ 2 5 ~
X	f6		ESC [ 1 6 ~	ESC [ 2 6 ~
X	f7		ESC [ 1 7 ~	ESC [ 2 7 ~
X	f8		ESC [ 1 8 ~	ESC [ 2 8 ~
X.fi
X
XThese are the codes sent in \fIopen\fR mode. In \fInormal\fR mode a line feed
Xcharacter is appended so the keys can be aliased to shell commands.
X	
X.sh "Other sent codes"
X.DT
X.nf
X	\fISequence\fR		\fIFunction\fR
X	ESC [ ? ? 8;7;5 c		Report Terminal Type
X	ESC [ ? r;c C		Report Window Size\(dg
X.\"	ESC [ ? r;c;b R		Report Mouse Event
X	ESC [ ? r0;c0;r1;c1;b Q	Report Mouse Event
X	ESC [ ? r0;c0;r1;c1;k S	Report Selection
X	ESC [ ? c LF		Report Resize Event
X.fi
X.TP 5
X\(dg
XLinefeed appended if not in \fIopen\fR mode
X.PP
X\fBDescrition of these sequences\fR
X.TP 15
X\fBReport Window Size\fR
X\fIr\fR is the number of rows, \fIc\fR the number of columns that fit into the
Xlayer. Note that a scroll bar reduces the usable display size by one column;
Xif a scrollbar is installed the actual window width is one smaller than what is
Xreported.
X.TP 
X\fBReport Mouse Event\fR
X.\"\fIr\fR, \fIc\fR give the one-relative coordinates of the mouse event in
X.\"character units. \fIB\fR describes the state of the mouse buttons
X.\"\fBafter\fR the event as a sum of the codes of the depressed buttons. For
X.\"the buttons codes see the description of \fIDefine Mouse Buttons\fR in
X.\"section \fIReceived codes\fR above. Mouse events in the scroll bar are
X.\"reported with \fIc\fR=0.
X\fIr0\fR, \fIc0\fR give one-relative coordinates where the first button was
Xpressed, \fIr1\fR, \fIc1\fR the coordinates where the last button was released.
XAll coordinates are in character units. \fIb\fR is the sum of the numbers of
Xthe buttons that were pressed. The right button has number 1, the middle button
Xnumber 2 and the left button number 4.
X.br
XIf the mouse is moved outside the layer while a button is pressed the mouse
Xevent is cancelled and not reported to the host.
X.TP 
X\fBReport Selection\fR
X\fIr0\fR, \fIc0\fR give the start, \fIr1\fR, \fIc1\fR the end coordinates of
Xthe selection, \fIk\fR gives the selection kind. Selection kind codes are:
X.br
X.nf
X	0	invalid selection
X	1	plain selection
X	2	copy selection
X	3	delete selection
X	4	move selection
X.TP 
X\fBReport Resize Event\fR
Xsequence sent by the emulator after the user has resized the layer. This can be
Xbound to a function resetting the terminal environment.
X.fi
X.PP
X.I 5620mtset
Xwrites to the standard output the string required to set the terminal
Xenvironment according to terminal capabilities and layer size. Normal use is
X.IP
Xeval `5620mtset`
X.LP
X\f2Csh\f1(1) users must
X.IP
Xset noglob
X.LP
Xfirst. They conveniently define an alias
X.IP
Xalias mtset 'set noglob; eval `5620mtset`'
X.LP
Xin their .cshrc file. This allows to set the terminal environment using the
Xcommand
X.IP
Xmtset
X.LP
Xat any time from the shell (particularily from the .login file for remote
Xlogins). It is also advisable to alias the \fIreport resize event\fR sequence
Xto this command:
X.IP
Xalias <ESC>[?c mtset
X.LP
Xso the terminal environment is automatically adjusted when the layer is
Xresized.
X.PP
XThe \fI5620mtset\fR command accepts the following options:
X.TP 12
X\fB\-c\fP
XForce output to be in \f2csh\f1(1) compatible format. Useful in
X\fIcsh\fR scripts.
X.TP
X\fB\-f\fP
XFix tty state. Cloned layers initially are in a funny state preferred by
X\fImux\fR but rather useless otherwise. With this option that state is reverted
Xby running \fI5620mstty\fR.
X.TP
X\fB\-s\fP
XForce output to be in \f2sh\f1(1) compatible format. Useful in
X\fIsh\fR and \fIksh\fR scripts.
X.PP
X.I 5620mtset
Xis automatically executed when
X.I 5620m
Xis downloaded or a new \fI5620m\fR layer is cloned.
X.PP
X.I 5620mstty
Xfixes a funny tty state as set up by mux. This program is run implicitly by the
X-f option of \fI5620mtset\fR and is probably of no use otherwise.
X.PP
X.SH FILES
X.ta \w'${DMD}/lib/5620_mouse.m  'u
X/usr/jerq/bin/5620m	Shell script for downloading emulator.
X.br
X/usr/jerq/mbin/5620m.m	Emulator program.
X.br
X/usr/local/bin/5620mtset	Program to set terminal environment.
X.br
X/usr/local/bin/5620mstty	Program to fix tty state.
X.SH "SEE ALSO"
Xemacs(1), mux(9), term(9).
X.br
XOlivetti AT&T
X.I 5620 Dot Mapped Display Owner's Manual
X.SH DIAGNOSTICS
X.I 5620m
Xprints an error message and exits with status 1 if not run under mux. Otherwise
Xthe exit status is 0.
X.SH "BUGS and RESTRICTIONS"
X.I 5620_mouse
Xdoesn't examine \f2stty\f1(1) options nor the 5620 `preferences'
Xsettings. Therefore, such options
Xas arbitrary tab settings are not available.
X.br
XThe 5620 `SET PF Key' sequence is not implemented.
X.br
XCloned layers will not survive their parent. Before the terminal emulator exits
Xin the parent layer (either by deleting the layer, by downloading another
Xprogram into it, or by explicitly exiting the emulator using the button 2 menu)
Xall cloned layers should be deleted or their emulator exited. Otherwise they
Xwill become useless.
X.br
XFonts are not handeled correctly. Loading new fonts may therefore lead to
Xunexpected results (like immediate emulator exit). One working alternative to
Xmux's ugly default font seems to be \fIdefont.nov20\fR.
END_OF_FILE
if test 17932 -ne `wc -c <'5620m/5620m.9'`; then
    echo shar: \"'5620m/5620m.9'\" unpacked with wrong size!
fi
# end of '5620m/5620m.9'
fi
echo shar: End of archive 2 \(of 3\).
cp /dev/null ark2isdone
MISSING=""
for I in 1 2 3 ; do
    if test ! -f ark${I}isdone ; then
	MISSING="${MISSING} ${I}"
    fi
done
if test "${MISSING}" = "" ; then
    echo You have unpacked all 3 archives.
    rm -f ark[1-9]isdone
else
    echo You still need to unpack the following archives:
    echo "        " ${MISSING}
fi
##  End of shell archive.
exit 0
-- 
Gernot Heiser <heiser at iis.UUCP> Phone:       +41 1/256 23 48
Integrated Systems Laboratory   CSNET/ARPA:  heiser%ifi.ethz.ch at relay.cs.net
ETH Zuerich                     EARN/BITNET: GRIDFILE at CZHETH5A
CH-8092 Zuerich, Switzerland    EUNET/UUCP:  {uunet,mcvax,...}!iis!heiser



More information about the Comp.sources.misc mailing list