diff options
author | piaip <piaip@63ad8ddf-47c3-0310-b6dd-a9e9d9715204> | 2007-11-30 23:45:10 +0800 |
---|---|---|
committer | piaip <piaip@63ad8ddf-47c3-0310-b6dd-a9e9d9715204> | 2007-11-30 23:45:10 +0800 |
commit | 85ffb389994fcfbe23e4258b40709bd0c6d5ce8a (patch) | |
tree | 8cc2003cf49807ba393d6f8d43b3706040abc15d /mbbsd | |
parent | 9512a651894b9f41d9d93284c2252c1134dc783c (diff) | |
download | pttbbs-85ffb389994fcfbe23e4258b40709bd0c6d5ce8a.tar pttbbs-85ffb389994fcfbe23e4258b40709bd0c6d5ce8a.tar.gz pttbbs-85ffb389994fcfbe23e4258b40709bd0c6d5ce8a.tar.bz2 pttbbs-85ffb389994fcfbe23e4258b40709bd0c6d5ce8a.tar.lz pttbbs-85ffb389994fcfbe23e4258b40709bd0c6d5ce8a.tar.xz pttbbs-85ffb389994fcfbe23e4258b40709bd0c6d5ce8a.tar.zst pttbbs-85ffb389994fcfbe23e4258b40709bd0c6d5ce8a.zip |
- edit.c: enable syntax highlight for pmore movie.
- edit.c: prepare for better attributed edit_outs
- pmore.c: export movie frame header parser
git-svn-id: http://opensvn.csie.org/pttbbs/trunk/pttbbs@3596 63ad8ddf-47c3-0310-b6dd-a9e9d9715204
Diffstat (limited to 'mbbsd')
-rw-r--r-- | mbbsd/edit.c | 186 | ||||
-rw-r--r-- | mbbsd/pmore.c | 66 |
2 files changed, 148 insertions, 104 deletions
diff --git a/mbbsd/edit.c b/mbbsd/edit.c index afbdbf56..f129c1fa 100644 --- a/mbbsd/edit.c +++ b/mbbsd/edit.c @@ -252,7 +252,6 @@ int fix_cursor(char *str, int pos, unsigned int dir) #endif - /* 記憶體管理與編輯處理 */ static void indigestion(int i) @@ -1939,25 +1938,34 @@ block_select(void) curr_buf->blockline = curr_buf->currline; } +enum { + EOATTR_NORMAL = 0x00, + EOATTR_SELECTED = 0x01, // selected (reverse) + EOATTR_MOVIECODE= 0x02, // pmore movie + +}; + /** * Just like outs, but print out '*' instead of 27(decimal) in the given string. * * FIXME column could not start from 0 */ -void -edit_outs(const char *text) -{ - edit_outs_n(text, scr_cols); -} - -void -edit_outs_n(const char *text, int n) +static void +edit_outs_attr_n(const char *text, int n, int attr) { int column = 0; - register unsigned char inAnsi = 0; register unsigned char ch; + int doReset = 0; + const char *reset = ANSI_RESET; + + if (attr & EOATTR_MOVIECODE) + { + reset = ANSI_COLOR(0;36); + doReset = 1; + outs(reset); + } #ifdef DBCSAWARE /* 0 = N/A, 1 = leading byte printed, 2 = ansi in middle */ @@ -1966,7 +1974,7 @@ edit_outs_n(const char *text, int n) while ((ch = *text++) && (++column < t_columns) && n-- > 0) { - if(inAnsi) + if(inAnsi == 1) { if(ch == ESC_CHR) outc('*'); @@ -1977,11 +1985,11 @@ edit_outs_n(const char *text, int n) if(!ANSI_IN_ESCAPE(ch)) { inAnsi = 0; - outs(ANSI_RESET); + outs(reset); } } - } + } else if(ch == ESC_CHR) { inAnsi = 1; @@ -2020,38 +2028,18 @@ edit_outs_n(const char *text, int n) } } - if(inAnsi) + if(inAnsi || doReset) outs(ANSI_RESET); } static void -edit_ansi_outs(const char *str) +edit_outs_attr(const char *text, int attr) { - char c; - while ((c = *str++)) { - if(c == ESC_CHR && *str == '*') - { - // ptt prints - /* Because moving within ptt_prints is too hard - * let's just display it as-is. - */ - outc('*'); - /* - char buf[64] = ESC_STR "*x"; - - str ++; - buf[2] = *str++; - Ptt_prints(buf, NO_RELOAD); - outs(buf); - */ - } else { - outc(c); - } - } + edit_outs_attr_n(text, scr_cols, attr); } static void -edit_ansi_outs_n(const char *str, int n) +edit_ansi_outs_n(const char *str, int n, int attr) { char c; while (n-- > 0 && (c = *str++)) { @@ -2062,30 +2050,49 @@ edit_ansi_outs_n(const char *str, int n) * let's just display it as-is. */ outc('*'); - /* - char buf[64] = ESC_STR "*x"; - - str ++; - buf[2] = *str++; - Ptt_prints(buf, NO_RELOAD); - if(strlen(buf) > n+1) - buf[n+1] = 0; - outs(buf); - n -= strlen(buf); - */ } else { outc(c); } } } +static void +edit_ansi_outs(const char *str, int attr) +{ + return edit_ansi_outs_n(str, strlen(str), attr); +} + +// old compatible API +void +edit_outs(const char *text) +{ + edit_outs_attr(text, 0); +} + +void +edit_outs_n(const char *text, int n) +{ + edit_outs_attr_n(text, n, 0); +} + + +#define PMORE_USE_ASCII_MOVIE // disable this if you don't enable ascii movie + +#ifdef PMORE_USE_ASCII_MOVIE +// pmore movie header support +unsigned char * + mf_movieFrameHeader(unsigned char *p, unsigned char *end); + +#endif // PMORE_USE_ASCII_MOVIE + static inline void display_textline_internal(textline_t *p, int i, int min, int max) { - char inblock; short tmp; - void (*output)(const char *); - void (*output_n)(const char *, int); + void (*output)(const char *, int) = edit_outs_attr; + void (*output_n)(const char *, int, int)= edit_outs_attr_n; + + int attr = EOATTR_NORMAL; move(i, 0); clrtoeol(); @@ -2099,30 +2106,45 @@ display_textline_internal(textline_t *p, int i, int min, int max) output = edit_ansi_outs; output_n = edit_ansi_outs_n; } - else { - output = edit_outs; - output_n = edit_outs_n; - } tmp = curr_buf->currln - curr_buf->curr_window_line + i; - /* if line 'i' is in block's range */ - if (has_block_selection() && ( - (curr_buf->blockln <= curr_buf->currln && - curr_buf->blockln <= tmp && tmp <= curr_buf->currln) || - (curr_buf->currln <= tmp && tmp <= curr_buf->blockln)) ) { - outs(ANSI_COLOR(7)); - inblock = 1; - } else - inblock = 0; + // parse attribute of line + + // selected attribute? + if (has_block_selection() && + ( (curr_buf->blockln <= curr_buf->currln && + curr_buf->blockln <= tmp && tmp <= curr_buf->currln) || + (curr_buf->currln <= tmp && tmp <= curr_buf->blockln)) ) + { + outs(ANSI_COLOR(7)); // remove me when EOATTR is ready... + attr |= EOATTR_SELECTED; + } - if (curr_buf->currln == curr_buf->blockln && p == curr_buf->currline && max > min) { - outs(ANSI_RESET); - (*output_n)(p->data, min); - outs(ANSI_COLOR(7)); - (*output_n)(p->data + min, max - min); + // movie attribute? +#ifdef PMORE_USE_ASCII_MOVIE + if (mf_movieFrameHeader( + (unsigned char*)p->data, + (unsigned char*)p->data + p->len)) + attr |= EOATTR_MOVIECODE; +#endif // PMORE_USE_ASCII_MOVIE + + // special: partial in block selection + if (curr_buf->currln == curr_buf->blockln && + p == curr_buf->currline && max > min) { + + outs(ANSI_RESET); // remove me when EOATTR is ready... + (*output_n)(p->data, min, attr); + + attr |= EOATTR_SELECTED; + outs(ANSI_COLOR(7)); // remove me when EOATTR is ready... + (*output_n)(p->data + min, max - min, attr); + + attr &= ~EOATTR_SELECTED; + outs(ANSI_RESET); // remove me when EOATTR is ready... + (*output)(p->data + max, attr); outs(ANSI_RESET); - (*output)(p->data + max); + } else #ifdef DBCSAWARE @@ -2130,12 +2152,15 @@ display_textline_internal(textline_t *p, int i, int min, int max) { if(curr_buf->edit_margin >= p->len) { - (*output)(""); + (*output)("", attr); } else { + int newpnt = curr_buf->edit_margin; unsigned char *pdata = (unsigned char*)(&p->data[0] + curr_buf->edit_margin); + if(mbcs_mode) newpnt = fix_cursor(p->data, newpnt, FC_LEFT); + if(newpnt == curr_buf->edit_margin-1) { /* this should be always 'outs'? */ @@ -2143,14 +2168,14 @@ display_textline_internal(textline_t *p, int i, int min, int max) outs(ANSI_COLOR(1) "<" ANSI_RESET); pdata++; } - (*output)((char*)pdata); + (*output)((char*)pdata, attr); } } else #endif - (*output)((curr_buf->edit_margin < p->len) ? &p->data[curr_buf->edit_margin] : ""); + (*output)((curr_buf->edit_margin < p->len) ? &p->data[curr_buf->edit_margin] : "", attr); - if (inblock) + if (attr) outs(ANSI_RESET); } /** @@ -3345,7 +3370,16 @@ vedit(char *fpath, int saveheader, int *islocal) if (curr_buf->ansimode) outs(curr_buf->currline->data); else - edit_outs(&curr_buf->currline->data[curr_buf->edit_margin]); + { + int attr = EOATTR_NORMAL; +#ifdef PMORE_USE_ASCII_MOVIE + if (mf_movieFrameHeader( + (unsigned char*)curr_buf->currline->data, + (unsigned char*)curr_buf->currline->data + curr_buf->currline->len)) + attr |= EOATTR_MOVIECODE; +#endif // PMORE_USE_ASCII_MOVIE + edit_outs_attr(&curr_buf->currline->data[curr_buf->edit_margin], attr); + } edit_msg(); } } /* redraw */ @@ -3354,5 +3388,5 @@ vedit(char *fpath, int saveheader, int *islocal) exit_edit_buffer(); } -/* vim:sw=4 +/* vim:sw=4:nofoldenable */ diff --git a/mbbsd/pmore.c b/mbbsd/pmore.c index 0ff07c3a..82eb9035 100644 --- a/mbbsd/pmore.c +++ b/mbbsd/pmore.c @@ -7,12 +7,15 @@ * designed for unlimilited length(lines). * * "pmore" is "piaip's more", NOT "PTT's more"!!! - * pmore is designed for general BBS systems, not + * pmore is designed for general maple-family BBS systems, not * specific to any branch. * * Author: Hung-Te Lin (piaip), June 2005. * <piaip@csie.ntu.edu.tw> * All Rights Reserved. + * You are free to use, modify, redistribute this program + * in any BBS style systems, or any other non-commercial usage. + * You must keep these copyright infomration. * * MAJOR IMPROVEMENTS: * - Clean source code, and more readble to mortal @@ -30,17 +33,16 @@ * - ASCII Art movie support [done] * - Left-right wide navigation [done] * - Reenrtance for main procedure [done with little hack] - * - A new optimized terminal base system (piterm) - * - ASCII Art movie navigation keys + * - A new optimized terminal base system (piterm) [dropped] + * - ASCII Art movie navigation keys [pending] * - * - [2007, Movie Enhancement] * - New Invisible Frame Header Code [done] * - Traditional Movie Compatible Mode * - Playback Control (pause, stop, skip, loop) - * - Support Anti-anti-idle (ex, PCMan sends up-down) * - Interactive Movie (Hyper-text) - * - - * - Virtual Contatenate + * - Support Anti-anti-idle (ex, PCMan sends up-down) + * - Virtual Contatenate [pending] */ // --------------------------------------------------------------- <FEATURES> @@ -74,7 +76,7 @@ // Platform Related. NoSync is faster but if we don't have it... #ifdef MAP_NOSYNC -#define MF_MMAP_OPTION (MAP_NOSYNC) +#define MF_MMAP_OPTION (MAP_NOSYNC|MAP_SHARED) #else #define MF_MMAP_OPTION (MAP_SHARED) #endif @@ -101,7 +103,7 @@ * Usually these function assumes "mf" can be accessed. * - pmore_* are utility functions * - * DETAILS + * DETAIL * - The most tricky part of pmore is the design of "maxdisps" and "maxlinenoS". * What do they mean? "The pointer and its line number of last page". * - Because pmore is designed to work with very large files, it's costly to @@ -140,9 +142,9 @@ int debug = 0; #endif /* DBCS users tend to write unsigned char. let's make compiler happy */ -#define ustrlen(x) strlen((char*)x) -#define ustrchr(x,y) (unsigned char*)strchr((char*)x, y) -#define ustrrchr(x,y) (unsigned char*)strrchr((char*)x, y) +#define ustrlen(x) strlen((char*)x) +#define ustrchr(x,y) (unsigned char*)strchr((char*)x, y) +#define ustrrchr(x,y) (unsigned char*)strrchr((char*)x, y) // --------------------------------------------- <Defines and constants> @@ -162,10 +164,10 @@ int debug = 0; #define ESC_CHR '\x1b' // Common ANSI commands. -#define ANSI_RESET ESC_STR "[m" -#define ANSI_COLOR(x) ESC_STR "[" #x "m" +#define ANSI_RESET ESC_STR "[m" +#define ANSI_COLOR(x) ESC_STR "[" #x "m" +#define ANSI_CLRTOEND ESC_STR "[K" #define ANSI_MOVETO(y,x) ESC_STR "[" #y ";" #x "H" -#define ANSI_CLRTOEND ESC_STR "[K" #define ANSI_IN_ESCAPE(x) (((x) >= '0' && (x) <= '9') || \ (x) == ';' || (x) == ',' || (x) == '[') @@ -387,9 +389,9 @@ MF_Movie mfmovie; mfmovie.frameclk.tv_sec = 1; mfmovie.frameclk.tv_usec = 0; \ } +unsigned char * + mf_movieFrameHeader(unsigned char *p, unsigned char *end); - -MFPROTO unsigned char * mf_movieFrameHeader(unsigned char *p); int pmore_wait_key(struct timeval *ptv, int dorefresh); int mf_movieNextFrame(); int mf_movieSyncFrame(); @@ -1071,13 +1073,13 @@ mf_display() // detected only applies for first page. // since this is not very often, let's prevent // showing control codes. - if(mf_movieFrameHeader(mf.dispe)) + if(mf_movieFrameHeader(mf.dispe, mf.end)) MFDISP_SKIPCURLINE(); } else if(mfmovie.mode == MFDISP_MOVIE_UNKNOWN || mfmovie.mode == MFDISP_MOVIE_PLAYING) { - if(mf_movieFrameHeader(mf.dispe)) + if(mf_movieFrameHeader(mf.dispe, mf.end)) switch(mfmovie.mode) { @@ -2532,6 +2534,11 @@ mf_moviePromptPlaying() // char buf[16] = ""; const char *s = " >>> 動畫播放中... 可按 q 或 Ctrl-C 停止"; + if (mfmovie.optkeys) + { + s = " >>> 互動式動畫播放中... 可按 q 或 Ctrl-C 停止"; + } + move(b_lines, 0); outs(ANSI_RESET ANSI_COLOR(1;30;47)); w -= strlen(s); outs(s); @@ -2592,8 +2599,8 @@ mf_movieMaskedInput(int c) return 0; } -MFPROTO unsigned char * -mf_movieFrameHeader(unsigned char *p) +unsigned char * +mf_movieFrameHeader(unsigned char *p, unsigned char *end) { // ANSI has ESC_STR [8m as "Conceal" but // not widely supported, even PieTTY. @@ -2603,23 +2610,26 @@ mf_movieFrameHeader(unsigned char *p) static size_t szPatHeader = 12; // strlen(patHeader); static size_t szPatHeader2 = 10; // strlen(patHeader2); - if(mf.end - p < szPatHeader) - return NULL; + size_t sz = end - p; + if (sz < 1) return NULL; if(*p == 12) // ^L return p+1; + if (sz < 2) return NULL; if( *p == '^' && *(p+1) == 'L') return p+2; // Add more frame headers - if (memcmp(p, patHeader, szPatHeader) == 0) - return p + szPatHeader; - + if (sz < szPatHeader2) return NULL; if (memcmp(p, patHeader2, szPatHeader2) == 0) return p + szPatHeader2; + if (sz < szPatHeader) return NULL; + if (memcmp(p, patHeader, szPatHeader) == 0) + return p + szPatHeader; + return NULL; } @@ -2630,7 +2640,7 @@ mf_movieGotoFrame(int fno) while (fno > 0) { - while ( mf_movieFrameHeader(mf.disps) == NULL) + while ( mf_movieFrameHeader(mf.disps, mf.end) == NULL) { if (mf_forward(1) < 1) return 0; @@ -2653,7 +2663,7 @@ mf_movieCurrentFrameNo() do { - if ( mf_movieFrameHeader(mf.disps)) + if ( mf_movieFrameHeader(mf.disps, mf.end)) no++; if (mf.disps >= p) @@ -3143,7 +3153,7 @@ mf_movieNextFrame() { do { - unsigned char *p = mf_movieFrameHeader(mf.disps); + unsigned char *p = mf_movieFrameHeader(mf.disps, mf.end); if(p) { |