예제 #1
0
파일: terminal.c 프로젝트: rdebath/sgt
/*
 * Same as power_on(), but an external function.
 */
void term_pwron(void) {
    power_on();
    fix_cpos;
    disptop = scrtop;
    deselect();
    term_update();
}
예제 #2
0
파일: terminal.c 프로젝트: rdebath/sgt
/*
 * Attempt to scroll the scrollback. The second parameter gives the
 * position we want to scroll to; the first is +1 to denote that
 * this position is relative to the beginning of the scrollback, -1
 * to denote it is relative to the end, and 0 to denote that it is
 * relative to the current position.
 */
void term_scroll (int rel, int where) {
    int n = where * (cols+1);

    disptop = (rel < 0 ? scrtop :
	       rel > 0 ? sbtop : disptop) + n;
    if (disptop < sbtop)
	disptop = sbtop;
    if (disptop > scrtop)
	disptop = scrtop;
    update_sbar();
    term_update();
}
예제 #3
0
/* Update the %_terms table to map the term [zTerm] to the given rowid. */
static int index_insert_term(fulltext_vtab *v, const char *zTerm, int nTerm,
                             sqlite_int64 iDocid, DocList *p){
  sqlite_int64 iFirst;
  sqlite_int64 iIndexRow;
  DocList doclist;

  int rc = term_chunk_select(v, zTerm, nTerm, iDocid, &iFirst);
  if( rc==SQLITE_DONE ){
    docListInit(&doclist, DL_POSITIONS_OFFSETS, 0, 0);
    if( docListUpdate(&doclist, iDocid, p) ){
      rc = term_insert(v, zTerm, nTerm, iDocid, &doclist);
      docListDestroy(&doclist);
      return rc;
    }
    return SQLITE_OK;
  }
  if( rc!=SQLITE_ROW ) return SQLITE_ERROR;

  /* This word is in the index; add this document ID to its blob. */

  rc = term_select(v, zTerm, nTerm, iFirst, &iIndexRow, &doclist);
  if( rc!=SQLITE_OK ) return rc;

  if( docListUpdate(&doclist, iDocid, p) ){
    /* If the blob is too big, split it in half. */
    if( doclist.nData>CHUNK_MAX ){
      DocList half;
      if( docListSplit(&doclist, &half) ){
        rc = term_insert(v, zTerm, nTerm, firstDocid(&half), &half);
        docListDestroy(&half);
        if( rc!=SQLITE_OK ) goto err;
      }
    }
    rc = term_update(v, iIndexRow, &doclist);
  }

err:
  docListDestroy(&doclist);
  return rc;
}
예제 #4
0
static int index_delete_term(fulltext_vtab *v, const char *zTerm, int nTerm,
                             sqlite_int64 iDocid){
  sqlite_int64 iFirst;
  sqlite_int64 iIndexRow;
  DocList doclist;

  int rc = term_chunk_select(v, zTerm, nTerm, iDocid, &iFirst);
  if( rc!=SQLITE_ROW ) return SQLITE_ERROR;

  rc = term_select(v, zTerm, nTerm, iFirst, &iIndexRow, &doclist);
  if( rc!=SQLITE_OK ) return rc;

  if( docListUpdate(&doclist, iDocid, NULL) ){
    if( doclist.nData>0 ){
      rc = term_update(v, iIndexRow, &doclist);
    } else {  /* empty posting list */
      rc = term_delete(v, iIndexRow);
    }
  }
  docListDestroy(&doclist);
  return rc;
}
예제 #5
0
파일: terminal.c 프로젝트: rdebath/sgt
/*
 * Remove everything currently in `inbuf' and stick it up on the
 * in-memory display. There's a big state machine in here to
 * process escape sequences...
 */
void term_out(void) {
    int c;
    int must_update = FALSE;

    while ( (c = inbuf_getc()) != -1) {
#ifdef LOG
	{
	    static FILE *fp = NULL;
	    if (!fp) fp = fopen("putty.log", "wb");
	    if (fp) fputc (c, fp);
	}
#endif
	switch (termstate) {
	  case TOPLEVEL:
	    do_toplevel:
	    switch (c) {
	      case '\005':	       /* terminal type query */
		ldisc->send ("\033[?1;2c", 7);
		break;
	      case '\007':
		beep();
		disptop = scrtop;
		must_update = TRUE;
		break;
	      case '\b':
		if (curs_x == 0 && curs_y > 0)
		    curs_x = cols-1, curs_y--;
		else if (wrapnext)
		    wrapnext = FALSE;
		else
		    curs_x--;
		fix_cpos;
		disptop = scrtop;
		must_update = TRUE;
		break;
	      case '\016':
		cset = 1;
		break;
	      case '\017':
		cset = 0;
		break;
	      case '\033':
		termstate = SEEN_ESC;
		break;
	      case 0233:
		termstate = SEEN_CSI;
		esc_nargs = 1;
		esc_args[0] = ARG_DEFAULT;
		esc_query = FALSE;
		break;
	      case 0235:
		termstate = SEEN_OSC;
		esc_args[0] = 0;
		break;
	      case '\r':
		curs_x = 0;
		wrapnext = FALSE;
		fix_cpos;
		disptop = scrtop;
		must_update = TRUE;
		break;
	      case '\013':
	      case '\014':
	      case '\n':
		if (curs_y == marg_b)
		    scroll (marg_t, marg_b, 1, TRUE);
		else if (curs_y < rows-1)
		    curs_y++;
                if (cfg.lfhascr)
                    curs_x = 0;
		fix_cpos;
		wrapnext = FALSE;
		disptop = scrtop;
		nl_count++;
		break;
	      case '\t':
		do {
		    curs_x++;
		} while (curs_x < cols-1 && !tabs[curs_x]);
		if (curs_x >= cols)
		    curs_x = cols-1;
		{
		    unsigned long *old_cpos = cpos;
		    fix_cpos;
		    check_selection (old_cpos, cpos);
		}
		disptop = scrtop;
		must_update = TRUE;
		break;
	      default:
		if (c >= ' ' && c != 0234) {
		    if (wrapnext) {
			cpos[1] = ATTR_WRAPPED;
			if (curs_y == marg_b)
			    scroll (marg_t, marg_b, 1, TRUE);
			else if (curs_y < rows-1)
			    curs_y++;
			curs_x = 0;
			fix_cpos;
			wrapnext = FALSE;
			nl_count++;
		    }
		    if (insert)
			insch (1);
		    check_selection (cpos, cpos+1);
		    *cpos++ = xlat_tty2scr((unsigned char)c) | curr_attr |
			(c <= 0x7F ? cset_attr[cset] : ATTR_ASCII);
		    curs_x++;
		    if (curs_x == cols) {
			cpos--;
			curs_x--;
			wrapnext = wrap;
		    }
		    disptop = scrtop;
		}
	    }
	    break;
	  case IGNORE_NEXT:
	    termstate = TOPLEVEL;
	    break;
	  case OSC_MAYBE_ST:
	    /*
	     * This state is virtually identical to SEEN_ESC, with the
	     * exception that we have an OSC sequence in the pipeline,
	     * and _if_ we see a backslash, we process it.
	     */
	    if (c == '\\') {
		do_osc();
		termstate = TOPLEVEL;
		break;
	    }
	    /* else fall through */
	  case SEEN_ESC:
	    termstate = TOPLEVEL;
	    switch (c) {
	      case '\005': case '\007': case '\b': case '\016': case '\017':
	      case '\033': case 0233: case 0234: case 0235: case '\r':
	      case '\013': case '\014': case '\n': case '\t':
		termstate = TOPLEVEL;
		goto do_toplevel;      /* hack... */
	      case ' ':		       /* some weird sequence? */
		termstate = IGNORE_NEXT;
		break;
	      case '[':		       /* enter CSI mode */
		termstate = SEEN_CSI;
		esc_nargs = 1;
		esc_args[0] = ARG_DEFAULT;
		esc_query = FALSE;
		break;
	      case ']':		       /* xterm escape sequences */
		termstate = SEEN_OSC;
		esc_args[0] = 0;
		break;
	      case '(':		       /* should set GL */
		termstate = SET_GL;
		break;
	      case ')':		       /* should set GR */
		termstate = SET_GR;
		break;
	      case '7':		       /* save cursor */
		save_cursor (TRUE);
		break;
	      case '8':		       /* restore cursor */
		save_cursor (FALSE);
		disptop = scrtop;
		must_update = TRUE;
		break;
	      case '=':
		app_keypad_keys = TRUE;
		break;
	      case '>':
		app_keypad_keys = FALSE;
		break;
	      case 'D':		       /* exactly equivalent to LF */
		if (curs_y == marg_b)
		    scroll (marg_t, marg_b, 1, TRUE);
		else if (curs_y < rows-1)
		    curs_y++;
		fix_cpos;
		wrapnext = FALSE;
		disptop = scrtop;
		nl_count++;
		break;
	      case 'E':		       /* exactly equivalent to CR-LF */
		curs_x = 0;
		wrapnext = FALSE;
		if (curs_y == marg_b)
		    scroll (marg_t, marg_b, 1, TRUE);
		else if (curs_y < rows-1)
		    curs_y++;
		fix_cpos;
		wrapnext = FALSE;
		nl_count++;
		disptop = scrtop;
		break;
	      case 'M':		       /* reverse index - backwards LF */
		if (curs_y == marg_t)
		    scroll (marg_t, marg_b, -1, TRUE);
		else if (curs_y > 0)
		    curs_y--;
		fix_cpos;
		wrapnext = FALSE;
		disptop = scrtop;
		must_update = TRUE;
		break;
	      case 'Z':		       /* terminal type query */
		ldisc->send ("\033[?6c", 5);
		break;
	      case 'c':		       /* restore power-on settings */
		power_on();
		fix_cpos;
		disptop = scrtop;
		must_update = TRUE;
		break;
	      case '#':		       /* ESC # 8 fills screen with Es :-) */
		termstate = SEEN_ESCHASH;
		break;
	      case 'H':		       /* set a tab */
		tabs[curs_x] = TRUE;
		break;
	    }
	    break;
	  case SEEN_CSI:
	    termstate = TOPLEVEL;      /* default */
	    switch (c) {
	      case '\005': case '\007': case '\b': case '\016': case '\017':
	      case '\033': case 0233: case 0234: case 0235: case '\r':
	      case '\013': case '\014': case '\n': case '\t':
		termstate = TOPLEVEL;
		goto do_toplevel;      /* hack... */
	      case '0': case '1': case '2': case '3': case '4':
	      case '5': case '6': case '7': case '8': case '9':
		if (esc_nargs <= ARGS_MAX) {
		    if (esc_args[esc_nargs-1] == ARG_DEFAULT)
			esc_args[esc_nargs-1] = 0;
		    esc_args[esc_nargs-1] =
			10 * esc_args[esc_nargs-1] + c - '0';
		}
		termstate = SEEN_CSI;
		break;
	      case ';':
		if (++esc_nargs <= ARGS_MAX)
		    esc_args[esc_nargs-1] = ARG_DEFAULT;
		termstate = SEEN_CSI;
		break;
	      case '?':
		esc_query = TRUE;
		termstate = SEEN_CSI;
		break;
	      case 'A':		       /* move up N lines */
		move (curs_x, curs_y - def(esc_args[0], 1), 1);
		disptop = scrtop;
		must_update = TRUE;
		break;
	      case 'B': case 'e':      /* move down N lines */
		move (curs_x, curs_y + def(esc_args[0], 1), 1);
		disptop = scrtop;
		must_update = TRUE;
		break;
	      case 'C': case 'a':      /* move right N cols */
		move (curs_x + def(esc_args[0], 1), curs_y, 1);
		disptop = scrtop;
		must_update = TRUE;
		break;
	      case 'D':		       /* move left N cols */
		move (curs_x - def(esc_args[0], 1), curs_y, 1);
		disptop = scrtop;
		must_update = TRUE;
		break;
	      case 'E':		       /* move down N lines and CR */
		move (0, curs_y + def(esc_args[0], 1), 1);
		disptop = scrtop;
		must_update = TRUE;
		break;
	      case 'F':		       /* move up N lines and CR */
		move (0, curs_y - def(esc_args[0], 1), 1);
		disptop = scrtop;
		must_update = TRUE;
		break;
	      case 'G': case '`':      /* set horizontal posn */
		move (def(esc_args[0], 1) - 1, curs_y, 0);
		disptop = scrtop;
		must_update = TRUE;
		break;
	      case 'd':		       /* set vertical posn */
		move (curs_x, (dec_om ? marg_t : 0) + def(esc_args[0], 1) - 1,
		      (dec_om ? 2 : 0));
		disptop = scrtop;
		must_update = TRUE;
		break;
	      case 'H': case 'f':      /* set horz and vert posns at once */
		if (esc_nargs < 2)
		    esc_args[1] = ARG_DEFAULT;
		move (def(esc_args[1], 1) - 1,
		      (dec_om ? marg_t : 0) + def(esc_args[0], 1) - 1,
		      (dec_om ? 2 : 0));
		disptop = scrtop;
		must_update = TRUE;
		break;
	      case 'J':		       /* erase screen or parts of it */
		{
		    unsigned int i = def(esc_args[0], 0) + 1;
		    if (i > 3)
			i = 0;
		    erase_lots(FALSE, !!(i & 2), !!(i & 1));
		}
		disptop = scrtop;
		must_update = TRUE;
		break;
	      case 'K':		       /* erase line or parts of it */
		{
		    unsigned int i = def(esc_args[0], 0) + 1;
		    if (i > 3)
			i = 0;
		    erase_lots(TRUE, !!(i & 2), !!(i & 1));
		}
		disptop = scrtop;
		must_update = TRUE;
		break;
	      case 'L':		       /* insert lines */
		if (curs_y <= marg_b)
		    scroll (curs_y, marg_b, -def(esc_args[0], 1), FALSE);
		disptop = scrtop;
		must_update = TRUE;
		break;
	      case 'M':		       /* delete lines */
		if (curs_y <= marg_b)
		    scroll (curs_y, marg_b, def(esc_args[0], 1), FALSE);
		disptop = scrtop;
		must_update = TRUE;
		break;
	      case '@':		       /* insert chars */
		insch (def(esc_args[0], 1));
		disptop = scrtop;
		must_update = TRUE;
		break;
	      case 'P':		       /* delete chars */
		insch (-def(esc_args[0], 1));
		disptop = scrtop;
		must_update = TRUE;
		break;
	      case 'c':		       /* terminal type query */
		ldisc->send ("\033[?6c", 5);
		break;
	      case 'n':		       /* cursor position query */
		if (esc_args[0] == 6) {
		    char buf[32];
		    sprintf (buf, "\033[%d;%dR", curs_y + 1, curs_x + 1);
		    ldisc->send (buf, strlen(buf));
		}
		break;
	      case 'h':		       /* toggle a mode to high */
		toggle_mode (esc_args[0], esc_query, TRUE);
		break;
	      case 'l':		       /* toggle a mode to low */
		toggle_mode (esc_args[0], esc_query, FALSE);
		break;
	      case 'g':		       /* clear tabs */
		if (esc_nargs == 1) {
		    if (esc_args[0] == 0) {
			tabs[curs_x] = FALSE;
		    } else if (esc_args[0] == 3) {
			int i;
			for (i = 0; i < cols; i++)
			    tabs[i] = FALSE;
		    }
		}
		break;
	      case 'r':		       /* set scroll margins */
		if (!esc_query && esc_nargs <= 2) {
		    int top, bot;
		    top = def(esc_args[0], 1) - 1;
		    if (top < 0)
			top = 0;
		    bot = (esc_nargs <= 1 || esc_args[1] == 0 ? rows :
			   def(esc_args[1], rows)) - 1;
		    if (bot >= rows)
			bot = rows-1;
		    if (top <= bot) {
			marg_t = top;
			marg_b = bot;
			curs_x = 0;
			/*
			 * I used to think the cursor should be
			 * placed at the top of the newly marginned
			 * area. Apparently not: VMS TPU falls over
			 * if so.
			 */
			curs_y = 0;
			fix_cpos;
			disptop = scrtop;
			must_update = TRUE;
		    }
		}
		break;
	      case 'm':		       /* set graphics rendition */
		{
		    int i;
		    for (i=0; i<esc_nargs; i++) {
			switch (def(esc_args[i], 0)) {
			  case 0:      /* restore defaults */
			    curr_attr = ATTR_DEFAULT; break;
			  case 1:      /* enable bold */
			    curr_attr |= ATTR_BOLD; break;
			  case 4:      /* enable underline */
			  case 21:     /* (enable double underline) */
			    curr_attr |= ATTR_UNDER; break;
			  case 7:      /* enable reverse video */
			    curr_attr |= ATTR_REVERSE; break;
			  case 22:     /* disable bold */
			    curr_attr &= ~ATTR_BOLD; break;
			  case 24:     /* disable underline */
			    curr_attr &= ~ATTR_UNDER; break;
			  case 27:     /* disable reverse video */
			    curr_attr &= ~ATTR_REVERSE; break;
			  case 30: case 31: case 32: case 33:
			  case 34: case 35: case 36: case 37:
			    /* foreground */
			    curr_attr &= ~ATTR_FGMASK;
			    curr_attr |= (esc_args[i] - 30) << ATTR_FGSHIFT;
			    break;
			  case 39:     /* default-foreground */
			    curr_attr &= ~ATTR_FGMASK;
			    curr_attr |= ATTR_DEFFG;
			    break;
			  case 40: case 41: case 42: case 43:
			  case 44: case 45: case 46: case 47:
			    /* background */
			    curr_attr &= ~ATTR_BGMASK;
			    curr_attr |= (esc_args[i] - 40) << ATTR_BGSHIFT;
			    break;
			  case 49:     /* default-background */
			    curr_attr &= ~ATTR_BGMASK;
			    curr_attr |= ATTR_DEFBG;
			    break;
			}
		    }
		}
		break;
	      case 's':		       /* save cursor */
		save_cursor (TRUE);
		break;
	      case 'u':		       /* restore cursor */
		save_cursor (FALSE);
		disptop = scrtop;
		must_update = TRUE;
		break;
	      case 't':		       /* set page size - ie window height */
		request_resize (cols, def(esc_args[0], 24));
		deselect();
		break;
	      case 'X':		       /* write N spaces w/o moving cursor */
		{
		    int n = def(esc_args[0], 1);
		    unsigned long *p = cpos;
		    if (n > cols - curs_x)
			n = cols - curs_x;
		    check_selection (cpos, cpos+n);
		    while (n--)
			*p++ = ERASE_CHAR;
		    disptop = scrtop;
		    must_update = TRUE;
		}
		break;
	      case 'x':		       /* report terminal characteristics */
		{
		    char buf[32];
		    int i = def(esc_args[0], 0);
		    if (i == 0 || i == 1) {
			strcpy (buf, "\033[2;1;1;112;112;1;0x");
			buf[2] += i;
			ldisc->send (buf, 20);
		    }
		}
		break;
	    }
	    break;
	  case SET_GL:
	  case SET_GR:
	    switch (c) {
	      case 'A':
		cset_attr[termstate == SET_GL ? 0 : 1] = ATTR_GBCHR;
		break;
	      case '0':
		cset_attr[termstate == SET_GL ? 0 : 1] = ATTR_LINEDRW;
		break;
	      default:		       /* specifically, 'B' */
		cset_attr[termstate == SET_GL ? 0 : 1] = ATTR_ASCII;
		break;
	    }
	    termstate = TOPLEVEL;
	    break;
	  case SEEN_OSC:
	    osc_w = FALSE;
	    switch (c) {
	      case '\005': case '\007': case '\b': case '\016': case '\017':
	      case '\033': case 0233: case 0234: case 0235: case '\r':
	      case '\013': case '\014': case '\n': case '\t':
		termstate = TOPLEVEL;
		goto do_toplevel;      /* hack... */
	      case 'P':		       /* Linux palette sequence */
		termstate = SEEN_OSC_P;
		osc_strlen = 0;
		break;
	      case 'R':		       /* Linux palette reset */
		palette_reset();
		term_invalidate();
		termstate = TOPLEVEL;
		break;
	      case 'W':		       /* word-set */
		termstate = SEEN_OSC_W;
		osc_w = TRUE;
		break;
	      case '0': case '1': case '2': case '3': case '4':
	      case '5': case '6': case '7': case '8': case '9':
		esc_args[0] = 10 * esc_args[0] + c - '0';
		break;
	      case 'L':
		/*
		 * Grotty hack to support xterm and DECterm title
		 * sequences concurrently.
		 */
		if (esc_args[0] == 2) {
		    esc_args[0] = 1;
		    break;
		}
		/* else fall through */
	      default:
		termstate = OSC_STRING;
		osc_strlen = 0;
	    }
	    break;
	  case OSC_STRING:
	    if (c == 0234 || c == '\007') {
		/*
		 * These characters terminate the string; ST and BEL
		 * terminate the sequence and trigger instant
		 * processing of it, whereas ESC goes back to SEEN_ESC
		 * mode unless it is followed by \, in which case it is
		 * synonymous with ST in the first place.
		 */
		do_osc();
		termstate = TOPLEVEL;
	    } else if (c == '\033')
		    termstate = OSC_MAYBE_ST;
	    else if (osc_strlen < OSC_STR_MAX)
		osc_string[osc_strlen++] = c;
	    break;
	  case SEEN_OSC_P:
	    {
		int max = (osc_strlen == 0 ? 21 : 16);
		int val;
		if (c >= '0' && c <= '9')
		    val = c - '0';
		else if (c >= 'A' && c <= 'A'+max-10)
		    val = c - 'A' + 10;
		else if (c >= 'a' && c <= 'a'+max-10)
		    val = c - 'a' + 10;
		else
		    termstate = TOPLEVEL;
		osc_string[osc_strlen++] = val;
		if (osc_strlen >= 7) {
		    palette_set (osc_string[0],
				 osc_string[1] * 16 + osc_string[2],
				 osc_string[3] * 16 + osc_string[4],
				 osc_string[5] * 16 + osc_string[6]);
		    term_invalidate();
		    termstate = TOPLEVEL;
		}
	    }
	    break;
	  case SEEN_OSC_W:
	    switch (c) {
	      case '\005': case '\007': case '\b': case '\016': case '\017':
	      case '\033': case 0233: case 0234: case 0235: case '\r':
	      case '\013': case '\014': case '\n': case '\t':
		termstate = TOPLEVEL;
		goto do_toplevel;      /* hack... */
	      case '0': case '1': case '2': case '3': case '4':
	      case '5': case '6': case '7': case '8': case '9':
		esc_args[0] = 10 * esc_args[0] + c - '0';
		break;
	      default:
		termstate = OSC_STRING;
		osc_strlen = 0;
	    }
	    break;
	  case SEEN_ESCHASH:
	    if (c == '8') {
		unsigned long *p = scrtop;
		int n = rows * (cols+1);
		while (n--)
		    *p++ = ATTR_DEFAULT | 'E';
		disptop = scrtop;
		must_update = TRUE;
		check_selection (scrtop, scrtop + rows * (cols+1));
	    }
	    termstate = TOPLEVEL;
	    break;
	}
	check_selection (cpos, cpos+1);
    }
	
    if (must_update || nl_count > MAXNL)
	term_update();
}
예제 #6
0
파일: terminal.c 프로젝트: rdebath/sgt
/*
 * Set up the terminal for a given size.
 */
void term_size(int newrows, int newcols, int newsavelines) {
    unsigned long *newtext, *newdisp, *newwant, *newalt;
    int i, j, crows, ccols;

    if (newrows == rows && newcols == cols && newsavelines == savelines)
	return;			       /* nothing to do */

    alt_t = marg_t = 0;
    alt_b = marg_b = newrows - 1;

    newtext = smalloc ((newrows+newsavelines)*(newcols+1)*TSIZE);
    disptop = newtext + newsavelines*(newcols+1);
    for (i=0; i<(newrows+newsavelines)*(newcols+1); i++)
	newtext[i] = ERASE_CHAR;
    if (rows != -1) {
	crows = rows + (scrtop - sbtop) / (cols+1);
	if (crows > newrows+newsavelines)
	    crows = newrows+newsavelines;
	ccols = (cols < newcols ? cols : newcols);
	for (i=0; i<crows; i++) {
	    int oldidx = (rows + savelines - crows + i) * (cols+1);
	    int newidx = (newrows + newsavelines - crows + i) * (newcols+1);
	    for (j=0; j<ccols; j++)
		newtext[newidx+j] = text[oldidx+j];
	    newtext[newidx+newcols] =
		(cols == newcols ? text[oldidx+cols] : 0);
	}
	sbtop = disptop - (crows - newrows) * (newcols+1);
	if (sbtop > disptop)
	    sbtop = disptop;
    } else
	sbtop = disptop;
    scrtop = disptop;
    sfree (text);
    text = newtext;

    newdisp = smalloc (newrows*(newcols+1)*TSIZE);
    for (i=0; i<newrows*(newcols+1); i++)
	newdisp[i] = ATTR_INVALID;
    sfree (disptext);
    disptext = newdisp;

    newwant = smalloc (newrows*(newcols+1)*TSIZE);
    for (i=0; i<newrows*(newcols+1); i++)
	newwant[i] = ATTR_INVALID;
    sfree (wanttext);
    wanttext = newwant;

    newalt = smalloc (newrows*(newcols+1)*TSIZE);
    for (i=0; i<newrows*(newcols+1); i++)
	newalt[i] = ERASE_CHAR;
    sfree (alttext);
    alttext = newalt;

    sfree (selspace);
    selspace = smalloc ( (newrows+newsavelines) * (newcols+sizeof(sel_nl)) );

    tabs = srealloc (tabs, newcols*sizeof(*tabs));
    {
	int i;
	for (i = (cols > 0 ? cols : 0); i < newcols; i++)
	    tabs[i] = (i % 8 == 0 ? TRUE : FALSE);
    }

    if (rows > 0)
	curs_y += newrows - rows;
    if (curs_y < 0)
	curs_y = 0;
    if (curs_y >= newrows)
	curs_y = newrows-1;
    if (curs_x >= newcols)
	curs_x = newcols-1;
    alt_x = alt_y = 0;
    wrapnext = alt_wnext = FALSE;

    rows = newrows;
    cols = newcols;
    savelines = newsavelines;
    fix_cpos;

    deselect();
    update_sbar();
    term_update();
}
예제 #7
0
파일: terminal.c 프로젝트: rdebath/sgt
void term_deselect (void) {
    deselect();
    term_update();
}
예제 #8
0
파일: terminal.c 프로젝트: rdebath/sgt
void term_mouse (Mouse_Button b, Mouse_Action a, int x, int y) {
    unsigned long *selpoint;
    
    if (y<0) y = 0;
    if (y>=rows) y = rows-1;
    if (x<0) {
        if (y > 0) {
            x = cols-1;
            y--;
        } else
            x = 0;
    }
    if (x>=cols) x = cols-1;

    selpoint = disptop + y * (cols+1) + x;

    if (b == MB_SELECT && a == MA_CLICK) {
	deselect();
	selstate = ABOUT_TO;
	selanchor = selpoint;
	selmode = SM_CHAR;
    } else if (b == MB_SELECT && (a == MA_2CLK || a == MA_3CLK)) {
	deselect();
	selmode = (a == MA_2CLK ? SM_WORD : SM_LINE);
	selstate = DRAGGING;
	selstart = selanchor = selpoint;
	selend = selstart + 1;
	sel_spread();
    } else if ((b == MB_SELECT && a == MA_DRAG) ||
	       (b == MB_EXTEND && a != MA_RELEASE)) {
	if (selstate == ABOUT_TO && selanchor == selpoint)
	    return;
	if (b == MB_EXTEND && a != MA_DRAG && selstate == SELECTED) {
	    if (selpoint-selstart < (selend-selstart)/2)
		selanchor = selend - 1;
	    else
		selanchor = selstart;
	    selstate = DRAGGING;
	}
	if (selstate != ABOUT_TO && selstate != DRAGGING)
	    selanchor = selpoint;
	selstate = DRAGGING;
	if (selpoint < selanchor) {
	    selstart = selpoint;
	    selend = selanchor + 1;
	} else {
	    selstart = selanchor;
	    selend = selpoint + 1;
	}
	sel_spread();
    } else if ((b == MB_SELECT || b == MB_EXTEND) && a == MA_RELEASE) {
	if (selstate == DRAGGING) {
	    /*
	     * We've completed a selection. We now transfer the
	     * data to the clipboard.
	     */
	    unsigned char *p = selspace;
	    unsigned long *q = selstart;

	    while (q < selend) {
		int nl = FALSE;
		unsigned long *lineend = q - (q-text) % (cols+1) + cols;
		unsigned long *nlpos = lineend;

		if (!(*nlpos & ATTR_WRAPPED)) {
		    while ((nlpos[-1] & CHAR_MASK) == 0x20 && nlpos > q)
			nlpos--;
		    if (nlpos < selend)
			nl = TRUE;
		}
		while (q < nlpos && q < selend)
		    *p++ = (unsigned char) (*q++ & CHAR_MASK);
		if (nl) {
		    int i;
		    for (i=0; i<sizeof(sel_nl); i++)
			*p++ = sel_nl[i];
		}
		q = lineend + 1;       /* start of next line */
	    }
	    write_clip (selspace, p - selspace);
	    selstate = SELECTED;
	} else
	    selstate = NO_SELECTION;
    } else if (b == MB_PASTE && (a==MA_CLICK || a==MA_2CLK || a==MA_3CLK)) {
	char *data;
	int len;

	get_clip((void **) &data, &len);
	if (data) {
	    char *p, *q;
	    p = q = data;
	    while (p < data+len) {
		while (p < data+len &&
		       !(p <= data+len-sizeof(sel_nl) &&
			 !memcmp(p, sel_nl, sizeof(sel_nl))))
		    p++;

		{
		    int i;
		    unsigned char c;
		    for(i=0;i<p-q;i++)
		    {
			c=xlat_kbd2tty(q[i]);
			ldisc->send(&c,1);
		    }
		}

		if (p <= data+len-sizeof(sel_nl) &&
		    !memcmp(p, sel_nl, sizeof(sel_nl))) {
		    ldisc->send ("\r", 1);
		    p += sizeof(sel_nl);
		}
		q = p;
	    }
	}
	get_clip(NULL, NULL);
    }

    term_update();
}
예제 #9
0
/* return true if command handled */
void readline_handle_byte(int ch)
{
    switch(term_esc_state) {
    case IS_NORM:
        switch(ch) {
        case 1:
            term_bol();
            break;
        case 4:
            term_delete_char();
            break;
        case 5:
            term_eol();
            break;
        case 9:
            term_completion();
            break;
        case 10:
        case 13:
            term_cmd_buf[term_cmd_buf_size] = '\0';
            if (!term_is_password)
                term_hist_add(term_cmd_buf);
            term_printf("\n");
            term_cmd_buf_index = 0;
            term_cmd_buf_size = 0;
            term_last_cmd_buf_index = 0;
            term_last_cmd_buf_size = 0;
            /* NOTE: readline_start can be called here */
            term_readline_func(term_readline_opaque, term_cmd_buf);
            break;
        case 23:
            /* ^W */
            term_backword();
            break;
        case 27:
            term_esc_state = IS_ESC;
            break;
        case 127:
        case 8:
            term_backspace();
            break;
	case 155:
            term_esc_state = IS_CSI;
	    break;
        default:
            if (ch >= 32) {
                term_insert_char(ch);
            }
            break;
        }
        break;
    case IS_ESC:
        if (ch == '[') {
            term_esc_state = IS_CSI;
            term_esc_param = 0;
        } else {
            term_esc_state = IS_NORM;
        }
        break;
    case IS_CSI:
        switch(ch) {
	case 'A':
	case 'F':
	    term_up_char();
	    break;
	case 'B':
	case 'E':
	    term_down_char();
	    break;
        case 'D':
            term_backward_char();
            break;
        case 'C':
            term_forward_char();
            break;
        case '0' ... '9':
            term_esc_param = term_esc_param * 10 + (ch - '0');
            goto the_end;
        case '~':
            switch(term_esc_param) {
            case 1:
                term_bol();
                break;
            case 3:
                term_delete_char();
                break;
            case 4:
                term_eol();
                break;
            }
            break;
        default:
            break;
        }
        term_esc_state = IS_NORM;
    the_end:
        break;
    }
    term_update();
}