⭐ 欢迎来到虫虫下载站! | 📦 资源下载 📁 资源专辑 ℹ️ 关于我们
⭐ 虫虫下载站

📄 screen.c

📁 rxvt经典的linux下的终端.小巧实用
💻 C
📖 第 1 页 / 共 5 页
字号:
/*--------------------------------*-C-*--------------------------------------* * File:	screen.c *---------------------------------------------------------------------------* * $Id: screen.c,v 1.258 2003/03/23 16:55:50 gcw Exp $ * * Copyright (c) 1997-2001 Geoff Wing <gcw@pobox.com> * * This program is free software; you can redistribute it and/or modify * it under the terms of the GNU General Public License as published by * the Free Software Foundation; either version 2 of the License, or * (at your option) any later version. * * This program is distributed in the hope that it will be useful, * but WITHOUT ANY WARRANTY; without even the implied warranty of * MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE.  See the * GNU General Public License for more details. * * You should have received a copy of the GNU General Public License * along with this program; if not, write to the Free Software * Foundation, Inc., 675 Mass Ave, Cambridge, MA 02139, USA. *--------------------------------------------------------------------------*//* * We handle _all_ screen updates and selections */#include "../config.h"		/* NECESSARY */#define INTERN_SCREEN#include "rxvt.h"		/* NECESSARY */#include "screen.intpro"	/* PROTOS for internal routines */#include <X11/Xmd.h>		/* get the typedef for CARD32 *//* ------------------------------------------------------------------------- */#ifdef MULTICHAR_SET#define RESET_CHSTAT(H)				\    if ((H)->chstat == WBYTE)			\	(H)->chstat = SBYTE, (H)->lost_multi = 1const KNOWN_ENCODINGS known_encodings[] = {    { SJIS, rxvt_sjis2jis, "sjis" },    { EUCJ, rxvt_euc2jis, "eucj" },    { GB, rxvt_euc2jis, "gb" },    { BIG5, rxvt_decodedummy, "big5" },    { EUCKR, rxvt_euc2jis, "kr" },    { NOENC, rxvt_decodedummy, "noenc" },    { 0, NULL, NULL }};#else# define RESET_CHSTAT(H)#endif/* ------------------------------------------------------------------------- */#define PROP_SIZE		16384#define TABSIZE			8	/* default tab size *//* ------------------------------------------------------------------------- * *             GENERAL SCREEN AND SELECTION UPDATE ROUTINES                  * * ------------------------------------------------------------------------- */#define ZERO_SCROLLBACK(R)						\    if (((R)->Options & Opt_scrollTtyOutput) == Opt_scrollTtyOutput)	\	(R)->TermWin.view_start = 0#define CLEAR_SELECTION(R)						\    (R)->selection.beg.row = (R)->selection.beg.col			\	= (R)->selection.end.row = (R)->selection.end.col = 0#define CLEAR_ALL_SELECTION(R)						\    (R)->selection.beg.row = (R)->selection.beg.col			\	= (R)->selection.mark.row = (R)->selection.mark.col		\	= (R)->selection.end.row = (R)->selection.end.col = 0#define ROW_AND_COL_IS_AFTER(A, B, C, D)				\    (((A) > (C)) || (((A) == (C)) && ((B) > (D))))#define ROW_AND_COL_IS_BEFORE(A, B, C, D)				\    (((A) < (C)) || (((A) == (C)) && ((B) < (D))))#define ROW_AND_COL_IN_ROW_AFTER(A, B, C, D)				\    (((A) == (C)) && ((B) > (D)))#define ROW_AND_COL_IN_ROW_AT_OR_AFTER(A, B, C, D)			\    (((A) == (C)) && ((B) >= (D)))#define ROW_AND_COL_IN_ROW_BEFORE(A, B, C, D)				\    (((A) == (C)) && ((B) < (D)))#define ROW_AND_COL_IN_ROW_AT_OR_BEFORE(A, B, C, D)			\    (((A) == (C)) && ((B) <= (D)))/* these must be row_col_t */#define ROWCOL_IS_AFTER(X, Y)						\    ROW_AND_COL_IS_AFTER((X).row, (X).col, (Y).row, (Y).col)#define ROWCOL_IS_BEFORE(X, Y)						\    ROW_AND_COL_IS_BEFORE((X).row, (X).col, (Y).row, (Y).col)#define ROWCOL_IN_ROW_AFTER(X, Y)					\    ROW_AND_COL_IN_ROW_AFTER((X).row, (X).col, (Y).row, (Y).col)#define ROWCOL_IN_ROW_BEFORE(X, Y)					\    ROW_AND_COL_IN_ROW_BEFORE((X).row, (X).col, (Y).row, (Y).col)#define ROWCOL_IN_ROW_AT_OR_AFTER(X, Y)					\    ROW_AND_COL_IN_ROW_AT_OR_AFTER((X).row, (X).col, (Y).row, (Y).col)#define ROWCOL_IN_ROW_AT_OR_BEFORE(X, Y)				\    ROW_AND_COL_IN_ROW_AT_OR_BEFORE((X).row, (X).col, (Y).row, (Y).col)/* * CLEAR_ROWS : clear <num> rows starting from row <row> * CLEAR_CHARS: clear <num> chars starting from pixel position <x,y> * ERASE_ROWS : set <num> rows starting from row <row> to the foreground colour */#define drawBuffer	(r->TermWin.vt)#define CLEAR_ROWS(row, num)						\    if (r->TermWin.mapped)						\	XClearArea(r->Xdisplay, drawBuffer, r->TermWin.int_bwidth,	\		   Row2Pixel(row), (unsigned int)r->TermWin.width,	\		   (unsigned int)Height2Pixel(num), False)#define CLEAR_CHARS(x, y, num)						\    if (r->TermWin.mapped)						\	XClearArea(r->Xdisplay, drawBuffer, x, y,			\		   (unsigned int)Width2Pixel(num),			\		   (unsigned int)Height2Pixel(1), False)#define ERASE_ROWS(row, num)						\    XFillRectangle(r->Xdisplay, drawBuffer, r->TermWin.gc,		\		   r->TermWin.int_bwidth, Row2Pixel(row),		\		   (unsigned int)r->TermWin.width,			\		   (unsigned int)Height2Pixel(num))/* ------------------------------------------------------------------------- * *                        SCREEN `COMMON' ROUTINES                           * * ------------------------------------------------------------------------- *//* Fill part/all of a line with blanks. *//* INTPROTO */voidrxvt_blank_line(text_t *et, rend_t *er, unsigned int width, rend_t efs){    MEMSET(et, ' ', (size_t)width);    efs &= ~RS_baseattrMask;    for (; width--;)	*er++ = efs;}/* ------------------------------------------------------------------------- *//* Fill a full line with blanks - make sure it is allocated first *//* INTPROTO */voidrxvt_blank_screen_mem(rxvt_t *r, text_t **tp, rend_t **rp, unsigned int row, rend_t efs){    int             width = r->TermWin.ncol;    rend_t         *er;#ifdef DEBUG_STRICT    assert((tp[row] && rp[row]) || (tp[row] == NULL && rp[row] == NULL));#endif    if (tp[row] == NULL) {	tp[row] = rxvt_malloc(sizeof(text_t) * width);	rp[row] = rxvt_malloc(sizeof(rend_t) * width);    }    MEMSET(tp[row], ' ', width);    efs &= ~RS_baseattrMask;    for (er = rp[row]; width--;)	*er++ = efs;}/* ------------------------------------------------------------------------- * *                          SCREEN INITIALISATION                            * * ------------------------------------------------------------------------- *//* EXTPROTO */voidrxvt_scr_reset(rxvt_t *r){    unsigned int    ncol, nrow, prev_ncol, prev_nrow,		    total_rows, prev_total_rows;    unsigned int    p, q;    int             k;    rend_t          setrstyle;    D_SCREEN((stderr, "rxvt_scr_reset()"));    r->TermWin.view_start = 0;    RESET_CHSTAT(r->h);    r->h->num_scr = 0;    prev_ncol = r->h->prev_ncol;    prev_nrow = r->h->prev_nrow;    if (r->TermWin.ncol == 0)	r->TermWin.ncol = 80;    if (r->TermWin.nrow == 0)	r->TermWin.nrow = 24;    ncol = r->TermWin.ncol;    nrow = r->TermWin.nrow;    if (ncol == prev_ncol && nrow == prev_nrow)	return;    r->h->want_refresh = 1;    total_rows = nrow + r->TermWin.saveLines;    prev_total_rows = prev_nrow + r->TermWin.saveLines;    r->screen.tscroll = 0;    r->screen.bscroll = nrow - 1;    if (prev_nrow == 0) {/* * A: first time called so just malloc everything : don't rely on realloc *    Note: this is still needed so that all the scrollback lines are NULL */	r->screen.text = rxvt_calloc(total_rows, sizeof(text_t *));	r->buf_text = rxvt_calloc(total_rows, sizeof(text_t *));	r->drawn_text = rxvt_calloc(nrow, sizeof(text_t *));	r->swap.text = rxvt_calloc(nrow, sizeof(text_t *));	r->screen.tlen = rxvt_calloc(total_rows, sizeof(int16_t));	r->swap.tlen = rxvt_calloc(nrow, sizeof(int16_t));	r->screen.rend = rxvt_calloc(total_rows, sizeof(rend_t *));	r->buf_rend = rxvt_calloc(total_rows, sizeof(rend_t *));	r->drawn_rend = rxvt_calloc(nrow, sizeof(rend_t *));	r->swap.rend = rxvt_calloc(nrow, sizeof(rend_t *));	for (p = 0; p < nrow; p++) {	    q = p + r->TermWin.saveLines;	    rxvt_blank_screen_mem(r, r->screen.text, r->screen.rend,				  q, DEFAULT_RSTYLE);	    rxvt_blank_screen_mem(r, r->swap.text, r->swap.rend,				  p, DEFAULT_RSTYLE);	    r->screen.tlen[q] = r->swap.tlen[p] = 0;	    rxvt_blank_screen_mem(r, r->drawn_text, r->drawn_rend,				  p, DEFAULT_RSTYLE);	}	MEMSET(r->h->charsets, 'B', sizeof(r->h->charsets));	r->TermWin.nscrolled = 0;	/* no saved lines */	r->h->rstyle = DEFAULT_RSTYLE;	r->screen.flags = Screen_DefaultFlags;	r->screen.cur.row = r->screen.cur.col = 0;	r->screen.charset = 0;	r->h->current_screen = PRIMARY;	rxvt_scr_cursor(r, SAVE);#if NSCREENS	r->swap.flags = Screen_DefaultFlags;	r->swap.cur.row = r->swap.cur.col = 0;	r->swap.charset = 0;	r->h->current_screen = SECONDARY;	rxvt_scr_cursor(r, SAVE);	r->h->current_screen = PRIMARY;#endif	r->selection.text = NULL;	r->selection.len = 0;	r->selection.op = SELECTION_CLEAR;	r->selection.screen = PRIMARY;	r->selection.clicks = 0;	CLEAR_ALL_SELECTION(r);	r->h->rvideo = 0;#ifdef MULTICHAR_SET	r->h->multi_byte = 0;	r->h->lost_multi = 0;	r->h->chstat = SBYTE;#endif    } else {/* * B1: add or delete rows as appropriate */	setrstyle = DEFAULT_RSTYLE;	if (nrow < prev_nrow) {	    /* delete rows */	    k = min(r->TermWin.nscrolled, prev_nrow - nrow);	    rxvt_scroll_text(r, 0, (int)prev_nrow - 1, k, 1);	    for (p = nrow; p < prev_nrow; p++) {		q = p + r->TermWin.saveLines;		if (r->screen.text[q]) {#ifdef DEBUG_STRICT		    assert(r->screen.rend[q]);#endif		    free(r->screen.text[q]);		    free(r->screen.rend[q]);		}		if (r->swap.text[p]) {#ifdef DEBUG_STRICT		    assert(r->swap.rend[p]);#endif		    free(r->swap.text[p]);		    free(r->swap.rend[p]);		}#ifdef DEBUG_STRICT		assert(r->drawn_text[p] && r->drawn_rend[p]);#endif		free(r->drawn_text[p]);		free(r->drawn_rend[p]);	    }	    /* we have fewer rows so fix up cursor position */	    MIN_IT(r->screen.cur.row, (int32_t)nrow - 1);	    MIN_IT(r->swap.cur.row, (int32_t)nrow - 1);	    rxvt_scr_reset_realloc(r);	/* realloc _last_ */	} else if (nrow > prev_nrow) {	    /* add rows */	    rxvt_scr_reset_realloc(r);	/* realloc _first_ */	    k = min(r->TermWin.nscrolled, nrow - prev_nrow);	    for (p = prev_total_rows; p < total_rows; p++) {		r->screen.tlen[p] = 0;		r->screen.text[p] = NULL;		r->screen.rend[p] = NULL;	    }	    for (p = prev_total_rows; p < total_rows - k; p++)		rxvt_blank_screen_mem(r, r->screen.text, r->screen.rend,				      p, setrstyle);	    for (p = prev_nrow; p < nrow; p++) {		r->swap.tlen[p] = 0;		r->swap.text[p] = NULL;		r->swap.rend[p] = NULL;		r->drawn_text[p] = NULL;		r->drawn_rend[p] = NULL;		rxvt_blank_screen_mem(r, r->swap.text, r->swap.rend,				      p, setrstyle);		rxvt_blank_screen_mem(r, r->drawn_text, r->drawn_rend,				      p, setrstyle);	    }	    if (k > 0) {		rxvt_scroll_text(r, 0, (int)nrow - 1, -k, 1);		r->screen.cur.row += k;		r->screen.s_cur.row += k;		r->TermWin.nscrolled -= k;	    }#ifdef DEBUG_STRICT	    assert(r->screen.cur.row < r->TermWin.nrow);	    assert(r->swap.cur.row < r->TermWin.nrow);#else				/* drive with your eyes closed */	    MIN_IT(r->screen.cur.row, nrow - 1);	    MIN_IT(r->swap.cur.row, nrow - 1);#endif	}/* B2: resize columns */	if (ncol != prev_ncol) {	    for (p = 0; p < total_rows; p++) {		if (r->screen.text[p]) {		    r->screen.text[p] = rxvt_realloc(r->screen.text[p],						     ncol * sizeof(text_t));		    r->screen.rend[p] = rxvt_realloc(r->screen.rend[p],						     ncol * sizeof(rend_t));		    MIN_IT(r->screen.tlen[p], (int16_t)ncol);		    if (ncol > prev_ncol)			rxvt_blank_line(&(r->screen.text[p][prev_ncol]),					&(r->screen.rend[p][prev_ncol]),					ncol - prev_ncol,					setrstyle);		}	    }	    for (p = 0; p < nrow; p++) {		r->drawn_text[p] = rxvt_realloc(r->drawn_text[p],						ncol * sizeof(text_t));		r->drawn_rend[p] = rxvt_realloc(r->drawn_rend[p],						ncol * sizeof(rend_t));		if (r->swap.text[p]) {		    r->swap.text[p] = rxvt_realloc(r->swap.text[p],						   ncol * sizeof(text_t));		    r->swap.rend[p] = rxvt_realloc(r->swap.rend[p],						   ncol * sizeof(rend_t));		    MIN_IT(r->swap.tlen[p], (int16_t)ncol);		    if (ncol > prev_ncol)			rxvt_blank_line(&(r->swap.text[p][prev_ncol]),					&(r->swap.rend[p][prev_ncol]),					ncol - prev_ncol, setrstyle);		}		if (ncol > prev_ncol)		    rxvt_blank_line(&(r->drawn_text[p][prev_ncol]),				    &(r->drawn_rend[p][prev_ncol]),				    ncol - prev_ncol, setrstyle);	    }	    MIN_IT(r->screen.cur.col, (int16_t)ncol - 1);	    MIN_IT(r->swap.cur.col, (int16_t)ncol - 1);	}	if (r->tabs)	    free(r->tabs);    }    r->tabs = rxvt_malloc(ncol * sizeof(char));    for (p = 0; p < ncol; p++)	r->tabs[p] = (p % TABSIZE == 0) ? 1 : 0;    r->h->prev_nrow = nrow;    r->h->prev_ncol = ncol;    rxvt_tt_winsize(r->cmd_fd, r->TermWin.ncol, r->TermWin.nrow);}/* INTPROTO */voidrxvt_scr_reset_realloc(rxvt_t *r){    u_int16_t       total_rows, nrow;    nrow = r->TermWin.nrow;    total_rows = nrow + r->TermWin.saveLines;/* *INDENT-OFF* */    r->screen.text = rxvt_realloc(r->screen.text, total_rows * sizeof(text_t *));    r->buf_text    = rxvt_realloc(r->buf_text   , total_rows * sizeof(text_t *));    r->drawn_text  = rxvt_realloc(r->drawn_text , nrow       * sizeof(text_t *));    r->swap.text   = rxvt_realloc(r->swap.text  , nrow       * sizeof(text_t *));    r->screen.tlen = rxvt_realloc(r->screen.tlen, total_rows * sizeof(int16_t));    r->swap.tlen   = rxvt_realloc(r->swap.tlen  , total_rows * sizeof(int16_t));    r->screen.rend = rxvt_realloc(r->screen.rend, total_rows * sizeof(rend_t *));    r->buf_rend    = rxvt_realloc(r->buf_rend   , total_rows * sizeof(rend_t *));    r->drawn_rend  = rxvt_realloc(r->drawn_rend , nrow       * sizeof(rend_t *));    r->swap.rend   = rxvt_realloc(r->swap.rend  , nrow       * sizeof(rend_t *));/* *INDENT-ON* */}/* ------------------------------------------------------------------------- *//* * Free everything.  That way malloc debugging can find leakage. *//* EXTPROTO */voidrxvt_scr_release(rxvt_t *r){    u_int16_t       total_rows;    int             i;    total_rows = r->TermWin.nrow + r->TermWin.saveLines;    for (i = 0; i < total_rows; i++) {	if (r->screen.text[i]) {	/* then so is r->screen.rend[i] */	    free(r->screen.text[i]);#ifdef DEBUG_STRICT	    assert(r->screen.rend[i]);#endif	    free(r->screen.rend[i]);	}    }    for (i = 0; i < r->TermWin.nrow; i++) {	free(r->drawn_text[i]);	free(r->drawn_rend[i]);	free(r->swap.text[i]);	free(r->swap.rend[i]);    }    free(r->screen.text);    free(r->screen.tlen);    free(r->screen.rend);    free(r->drawn_text);    free(r->drawn_rend);    free(r->swap.text);    free(r->swap.tlen);    free(r->swap.rend);    free(r->buf_text);

⌨️ 快捷键说明

复制代码 Ctrl + C
搜索代码 Ctrl + F
全屏模式 F11
切换主题 Ctrl + Shift + D
显示快捷键 ?
增大字号 Ctrl + =
减小字号 Ctrl + -