diff options
Diffstat (limited to 'mbbsd/read.c')
-rw-r--r-- | mbbsd/read.c | 620 |
1 files changed, 316 insertions, 304 deletions
diff --git a/mbbsd/read.c b/mbbsd/read.c index e92e6b48..72f7c837 100644 --- a/mbbsd/read.c +++ b/mbbsd/read.c @@ -232,27 +232,23 @@ static int cursor_pos(keeploc_t * locmem, int val, int from_top, int isshow) { int top=locmem->top_ln; - if (!last_line) - { - cursor_show(3 , 0); - return DONOTHING; - } - if (val > last_line) - { + if (!last_line){ + cursor_show(3 , 0); + return DONOTHING; + } + if (val > last_line){ bell(); val = last_line; - } - if (val <= 0) - { + } + if (val <= 0){ bell(); val = 1; - } + } if (val >= top && val < top + p_lines) { - if(isshow) - { - cursor_clear(3 + locmem->crs_ln - top, 0); - cursor_show(3 + val - top, 0); - } + if(isshow){ + cursor_clear(3 + locmem->crs_ln - top, 0); + cursor_show(3 + val - top, 0); + } locmem->crs_ln = val; return DONOTHING; } @@ -266,44 +262,41 @@ cursor_pos(keeploc_t * locmem, int val, int from_top, int isshow) static int thread(keeploc_t * locmem, int stypen) { - int pos = locmem->crs_ln, jump=200, new_ln; fileheader_t fh; - char *key = - stypen & RS_AUTHOR ? headers[pos - locmem->top_ln].owner : - (subject( stypen & RS_CURRENT ? - currtitle : - headers[pos - locmem->top_ln].title )); - int fd=-1, step = stypen & RS_FORWARD ? 1 : -1; - - for(new_ln = pos+step; - new_ln>0 && new_ln<=last_line && --jump>0; new_ln+=step) - { + int pos = locmem->crs_ln, jump = 200, new_ln; + int fd = -1, step = stypen & RS_FORWARD ? 1 : -1; + char *key = + (stypen & RS_AUTHOR ? headers[pos - locmem->top_ln].owner : + (subject( stypen & RS_CURRENT ? + currtitle : + headers[pos - locmem->top_ln].title ))); + + for(new_ln = pos + step ; + new_ln > 0 && new_ln <= last_line && --jump>0; + new_ln += step) { get_record_keep(currdirect, &fh, sizeof(fileheader_t), new_ln, &fd); - if(stypen & RS_TITLE) - { - if(stypen & RS_FIRST) - { - if(!strcmp(fh.title, key)) break; - } + if(stypen & RS_TITLE){ + if(stypen & RS_FIRST) { + if(!strcmp(fh.title, key)) break; + } else - if(!strcmp(subject(fh.title), key)) break; - } - else if(stypen & RS_NEWPOST) - { + if(!strcmp(subject(fh.title), key)) break; + } + else if(stypen & RS_NEWPOST){ if(strncmp(fh.title,"Re:",3)) break; - } - else // RS_AUTHOR - { + } + else{ // RS_AUTHOR if(!strcmp(subject(fh.owner), key)) break; - } - } - if(fd!=-1) close(fd); - if(jump <=0 || new_ln<=0 || new_ln>last_line) new_ln = pos; //didn't find - else - { - strncpy(currtitle, fh.title, TTLEN); - strncpy(currtitle, fh.title, TTLEN); - } + } + } + if( fd != -1 ) + close(fd); + if( jump <=0 || new_ln<=0 || new_ln > last_line ) + new_ln = pos; //didn't find + else{ + strncpy(currtitle, fh.title, TTLEN); + strncpy(currtitle, fh.title, TTLEN); + } return new_ln; } @@ -346,70 +339,74 @@ select_read(keeploc_t * locmem, int sr_mode) int len, fd, fr, i, count=0, reference = 0; fileheader_t *fh = &headers[locmem->crs_ln - locmem->top_ln]; - if(sr_mode & RS_AUTHOR) - { - if(!getdata_str(b_lines, 0, - currmode & MODE_SELECT ? "增加條件 作者:":"搜尋作者:", - keyword, IDLEN+1, LCECHO, fh->owner)) - return READ_REDRAW; - } - else if(sr_mode & RS_KEYWORD) - { - if(!getdata_str(b_lines, 0, - currmode & MODE_SELECT ? "增加條件 標題:":"搜尋標題:", - keyword, TTLEN, DOECHO, subject(fh->title))) - return READ_REDRAW; - } + if(sr_mode & RS_AUTHOR){ + if(!getdata_str(b_lines, 0, + currmode & MODE_SELECT ? "增加條件 作者:":"搜尋作者:", + keyword, IDLEN+1, LCECHO, fh->owner)) + return READ_REDRAW; + } + else if(sr_mode & RS_KEYWORD){ + if(!getdata_str(b_lines, 0, + currmode & MODE_SELECT ? "增加條件 標題:":"搜尋標題:", + keyword, TTLEN, DOECHO, subject(fh->title))) + return READ_REDRAW; + } else if(sr_mode & RS_TITLE) - strcpy(keyword, subject(fh->title)); + strcpy(keyword, subject(fh->title)); p = strstr(currdirect, "SR"); snprintf(genbuf, sizeof(genbuf), "%s.%X.%X", p ? p : "SR", sr_mode, StringHash(keyword)); - if(strlen(genbuf)>MAXPATHLEN-50) return READ_REDRAW; // avoid overflow + if( strlen(genbuf) > MAXPATHLEN - 50 ) + return READ_REDRAW; // avoid overflow if (currstat == RMAIL) - sethomefile(newdirect, cuser.userid, genbuf); + sethomefile(newdirect, cuser.userid, genbuf); else - setbfile(newdirect, currboard, genbuf); - - if(now - dasht(newdirect) > 600) - { - if ((fd = open(newdirect, O_CREAT | O_RDWR, 0600))==-1) return READ_REDRAW; - if ((fr = open(currdirect, O_RDONLY, 0)) != -1) { - while( (len = read(fr, fhs, sizeof(fhs))) > 0 ){ - len /= sizeof(fileheader_t); - for( i = 0 ; i < len ; ++i ){ - reference++; - if(sr_mode & RS_MARK && - !(fhs[i].filemode & FILE_MARKED)) continue; - if(sr_mode & RS_NEWPOST && - !strncmp(fhs[i].title, "Re:", 3)) continue; - if(sr_mode & RS_AUTHOR && - !strcasestr(fhs[i].owner, keyword)) continue; - if(sr_mode & RS_KEYWORD && - !strcasestr(fhs[i].title, keyword)) continue; - if(sr_mode & RS_TITLE && - strcmp(subject(fhs[i].title), keyword)) - continue; - count ++; - fhs[i].money = reference | FHR_REFERENCE; - write(fd, &fhs[i], sizeof(fileheader_t)); - } - } // end while + setbfile(newdirect, currboard, genbuf); + + if( !(now - dasht(newdirect) > 600) ) + count = dashs(newdirect); + else { + if( (fd = open(newdirect, O_CREAT | O_RDWR, 0600)) == -1 ) + return READ_REDRAW; + if( (fr = open(currdirect, O_RDONLY, 0)) != -1 ) { + while( (len = read(fr, fhs, sizeof(fhs))) > 0 ){ + len /= sizeof(fileheader_t); + for( i = 0 ; i < len ; ++i ){ + reference++; + if( sr_mode & RS_MARK && + !(fhs[i].filemode & FILE_MARKED) ) + continue; + if(sr_mode & RS_NEWPOST && + !strncmp(fhs[i].title, "Re:", 3)) + continue; + if(sr_mode & RS_AUTHOR && + !strcasestr(fhs[i].owner, keyword)) + continue; + if(sr_mode & RS_KEYWORD && + !strcasestr(fhs[i].title, keyword)) + continue; + if(sr_mode & RS_TITLE && + strcmp(subject(fhs[i].title), keyword)) + continue; + ++count; + fhs[i].money = reference | FHR_REFERENCE; + write(fd, &fhs[i], sizeof(fileheader_t)); + } + } // end while close(fr); - } - close(fd); - } - else - count = dashs(newdirect); + } + close(fd); + } + if(count) { - strlcpy(currdirect, newdirect, sizeof(currdirect)); - currmode |= MODE_SELECT; - return NEWDIRECT; - } + strlcpy(currdirect, newdirect, sizeof(currdirect)); + currmode |= MODE_SELECT; + return NEWDIRECT; + } return READ_REDRAW; } @@ -417,187 +414,199 @@ static int i_read_key(onekey_t * rcmdlist, keeploc_t * locmem, int bid, int bottom_line) { - int mode = DONOTHING; - int num, new_top=10; - char direct[60]; - static char default_ch=0; - int ch, new_ln= locmem->crs_ln, lastmode=0; + int mode = DONOTHING, num, new_top=10; + int ch, new_ln = locmem->crs_ln, lastmode=0; + char direct[60]; + static char default_ch = 0; do { - if((mode=cursor_pos(locmem, new_ln, new_top, default_ch?0:1))!=DONOTHING) - return mode; - - if(default_ch) - { - if(new_ln != locmem->crs_ln) - {default_ch=0; return FULLUPDATE;} // move fault - ch = default_ch; - } - else - ch = igetch(); - - new_top = 10; // default 10 - switch (ch) { - case '0': - case '1': - case '2': - case '3': - case '4': - case '5': - case '6': - case '7': - case '8': - case '9': - if((num = search_num(ch, last_line))!=-1) - new_ln = num+1; - break; + if( (mode = cursor_pos(locmem, new_ln, new_top, default_ch ? 0 : 1)) + != DONOTHING ) + return mode; + + if( !default_ch ) + ch = igetch(); + else{ + if(new_ln != locmem->crs_ln) {// move fault + default_ch=0; + return FULLUPDATE; + } + ch = default_ch; + } + + new_top = 10; // default 10 + switch (ch) { + case '0': case '1': case '2': case '3': case '4': + case '5': case '6': case '7': case '8': case '9': + if( (num = search_num(ch, last_line)) != -1 ) + new_ln = num + 1; + break; case 'q': case 'e': case KEY_LEFT: - if(currmode & MODE_SELECT){ - char genbuf[256]; - fileheader_t *fhdr = &headers[locmem->crs_ln - locmem->top_ln]; - board_select(); - setbdir(genbuf, currboard); - locmem = getkeep(genbuf, 0, 1); - locmem->crs_ln = - getindex(genbuf, fhdr->filename, sizeof(fileheader_t)); - num = locmem->crs_ln - p_lines + 1; - locmem->top_ln = num < 1 ? 1 : num; - mode = NEWDIRECT; - } - else - mode = (currmode & MODE_ETC) ? board_etc() : - (currmode & MODE_DIGEST) ? board_digest() : DOQUIT; - break; + if(currmode & MODE_SELECT){ + char genbuf[256]; + fileheader_t *fhdr = &headers[locmem->crs_ln - locmem->top_ln]; + board_select(); + setbdir(genbuf, currboard); + locmem = getkeep(genbuf, 0, 1); + locmem->crs_ln = + getindex(genbuf, fhdr->filename, sizeof(fileheader_t)); + num = locmem->crs_ln - p_lines + 1; + locmem->top_ln = num < 1 ? 1 : num; + mode = NEWDIRECT; + } + else + mode = (currmode & MODE_ETC) ? board_etc() : + (currmode & MODE_DIGEST) ? board_digest() : DOQUIT; + break; case Ctrl('L'): - redoscr(); - break; + redoscr(); + break; case Ctrl('H'): - mode = select_read(locmem, RS_NEWPOST); + mode = select_read(locmem, RS_NEWPOST); break; + case 'a': case 'A': - mode = select_read(locmem, RS_AUTHOR); - break; + mode = select_read(locmem, RS_AUTHOR); + break; + case 'G': - mode = select_read(locmem, RS_MARK); - break; + mode = select_read(locmem, RS_MARK); + break; + case '/': case '?': - mode = select_read(locmem, RS_KEYWORD); - break; + mode = select_read(locmem, RS_KEYWORD); + break; + case 'S': - mode = select_read(locmem, RS_TITLE); - break; + mode = select_read(locmem, RS_TITLE); + break; + case '=': - new_ln = thread(locmem, RELATE_FIRST); - break; + new_ln = thread(locmem, RELATE_FIRST); + break; + case '\\': - new_ln = thread(locmem, CURSOR_FIRST); - break; + new_ln = thread(locmem, CURSOR_FIRST); + break; + case ']': - new_ln = thread(locmem, RELATE_NEXT); - break; + new_ln = thread(locmem, RELATE_NEXT); + break; + case '+': - new_ln = thread(locmem, CURSOR_NEXT); - break; + new_ln = thread(locmem, CURSOR_NEXT); + break; + case '[': - new_ln = thread(locmem, RELATE_PREV); - break; + new_ln = thread(locmem, RELATE_PREV); + break; + case '-': - new_ln = thread(locmem, CURSOR_PREV); - break; + new_ln = thread(locmem, CURSOR_PREV); + break; + case '<': case ',': - new_ln = thread(locmem, NEWPOST_PREV); - break; + new_ln = thread(locmem, NEWPOST_PREV); + break; + case '.': case '>': - new_ln = thread(locmem, NEWPOST_NEXT); - break; + new_ln = thread(locmem, NEWPOST_NEXT); + break; + case 'p': case 'k': - case KEY_UP: - new_ln = locmem->crs_ln - 1; - new_top = p_lines - 2; - break; - case 'n': - case 'j': - case KEY_DOWN: - new_ln = locmem->crs_ln + 1; - new_top = 1; - break; - case ' ': - case KEY_PGDN: - case 'N': - case Ctrl('F'): - new_ln = locmem->top_ln + p_lines; - new_top = 0; - break; - case KEY_PGUP: - case Ctrl('B'): - case 'P': - new_ln = locmem->top_ln - p_lines; - new_top = 0; - break; - case KEY_END: - case '$': - new_ln = last_line; - new_top = p_lines-1; - break; - case 'F': - case 'U': - if (HAS_PERM(PERM_FORWARD)) { - mail_forward(&headers[locmem->crs_ln - locmem->top_ln], - currdirect, ch /* == 'U' */ ); - /* by CharlieL */ - mode = READ_REDRAW; - } - break; - case Ctrl('Q'): - mode = my_query(headers[locmem->crs_ln - locmem->top_ln].owner); - break; - case Ctrl('S'): - if (HAS_PERM(PERM_ACCOUNTS)) { - int id; - userec_t muser; - - strlcpy(currauthor, - headers[locmem->crs_ln - locmem->top_ln].owner, - sizeof(currauthor)); - stand_title("使用者設定"); - move(1, 0); - if ((id = getuser(headers[locmem->crs_ln - locmem->top_ln].owner))) - { - memcpy(&muser, &xuser, sizeof(muser)); - user_display(&muser, 1); - uinfo_query(&muser, 1, id); + case KEY_UP: + new_ln = locmem->crs_ln - 1; + new_top = p_lines - 2; + break; + + case 'n': + case 'j': + case KEY_DOWN: + new_ln = locmem->crs_ln + 1; + new_top = 1; + break; + + case ' ': + case KEY_PGDN: + case 'N': + case Ctrl('F'): + new_ln = locmem->top_ln + p_lines; + new_top = 0; + break; + + case KEY_PGUP: + case Ctrl('B'): + case 'P': + new_ln = locmem->top_ln - p_lines; + new_top = 0; + break; + + case KEY_END: + case '$': + new_ln = last_line; + new_top = p_lines-1; + break; + + case 'F': + case 'U': + if (HAS_PERM(PERM_FORWARD)) { + mail_forward(&headers[locmem->crs_ln - locmem->top_ln], + currdirect, ch /* == 'U' */ ); + /* by CharlieL */ + mode = READ_REDRAW; } - mode = FULLUPDATE; - } - break; + break; + + case Ctrl('Q'): + mode = my_query(headers[locmem->crs_ln - locmem->top_ln].owner); + break; + + case Ctrl('S'): + if (HAS_PERM(PERM_ACCOUNTS)) { + int id; + userec_t muser; + + strlcpy(currauthor, + headers[locmem->crs_ln - locmem->top_ln].owner, + sizeof(currauthor)); + stand_title("使用者設定"); + move(1, 0); + if ((id = getuser(headers[locmem->crs_ln - locmem->top_ln].owner))) { + memcpy(&muser, &xuser, sizeof(muser)); + user_display(&muser, 1); + uinfo_query(&muser, 1, id); + } + mode = FULLUPDATE; + } + break; - /* rocker.011018: 採用新的tag模式 */ - case 't': - /* 將原本在 Read() 裡面的 "TagNum = 0" 移至此處 */ - if ((currstat & RMAIL && TagBoard != 0) || + /* rocker.011018: 採用新的tag模式 */ + case 't': + /* 將原本在 Read() 裡面的 "TagNum = 0" 移至此處 */ + if ((currstat & RMAIL && TagBoard != 0) || (!(currstat & RMAIL) && TagBoard != bid)) { - if (currstat & RMAIL) - TagBoard = 0; - else - TagBoard = bid; - TagNum = 0; - } - /* rocker.011112: 解決再select mode標記文章的問題 */ - if (Tagger(atoi(headers[locmem->crs_ln - locmem->top_ln].filename + 2), - (currmode & MODE_SELECT) ? - (headers[locmem->crs_ln - locmem->top_ln].money & ~FHR_REFERENCE) : - locmem->crs_ln, TAG_TOGGLE)) - locmem->crs_ln = locmem->crs_ln + 1; - mode = PART_REDRAW; - break; + if (currstat & RMAIL) + TagBoard = 0; + else + TagBoard = bid; + TagNum = 0; + } + /* rocker.011112: 解決再select mode標記文章的問題 */ + if (Tagger(atoi(headers[locmem->crs_ln - locmem->top_ln].filename + 2), + (currmode & MODE_SELECT) ? + (headers[locmem->crs_ln - locmem->top_ln].money & ~FHR_REFERENCE) : + locmem->crs_ln, TAG_TOGGLE)) + locmem->crs_ln = locmem->crs_ln + 1; + mode = PART_REDRAW; + break; case Ctrl('C'): if (TagNum) { @@ -609,9 +618,11 @@ i_read_key(onekey_t * rcmdlist, keeploc_t * locmem, case Ctrl('T'): mode = TagThread(currdirect); break; + case Ctrl('D'): mode = TagPruner(bid); break; + case '\n': case '\r': case 'l': @@ -622,32 +633,29 @@ i_read_key(onekey_t * rcmdlist, keeploc_t * locmem, break; if (ch > 0 && ch <= onekey_size) { int (*func)() = rcmdlist[ch - 1]; - if (func != NULL) - { - num = locmem->crs_ln - bottom_line; + if (func != NULL){ + num = locmem->crs_ln - bottom_line; - if (num>0) - { + if( num > 0 ){ sprintf(direct,"%s.bottom", currdirect); - mode= (*func)(num, &headers[locmem->crs_ln-locmem->top_ln], - direct); - } - else + mode= (*func)(num, &headers[locmem->crs_ln-locmem->top_ln], + direct); + } + else mode = (*func)(locmem->crs_ln, - &headers[locmem->crs_ln - locmem->top_ln], currdirect); - if(mode == READ_SKIP) + &headers[locmem->crs_ln - locmem->top_ln], + currdirect); + if(mode == READ_SKIP) mode = lastmode; - // 以下這幾種 mode 要再處理游標 + // 以下這幾種 mode 要再處理游標 if(mode == READ_PREV || mode == READ_NEXT || mode == RELATE_PREV || mode == RELATE_FIRST || mode == AUTHOR_NEXT || mode == AUTHOR_PREV || - mode == RELATE_NEXT) - { - lastmode = mode; + mode == RELATE_NEXT){ + lastmode = mode; - switch(mode) - { + switch(mode){ case READ_PREV: new_ln = locmem->crs_ln - 1; break; @@ -669,17 +677,18 @@ i_read_key(onekey_t * rcmdlist, keeploc_t * locmem, case AUTHOR_NEXT: new_ln = thread(locmem, AUTHOR_NEXT); break; - } - mode = DONOTHING; default_ch = 'r'; - + } + mode = DONOTHING; default_ch = 'r'; } - else {default_ch = 0; lastmode=0;} - } //end if (func != NULL) - } // ch > 0 && ch <= onekey_size + else { + default_ch = 0; + lastmode = 0; + } + } //end if (func != NULL) + } // ch > 0 && ch <= onekey_size break; - } // end switch - } - while (mode == DONOTHING); + } // end switch + } while (mode == DONOTHING); return mode; } @@ -687,28 +696,31 @@ int get_records_and_bottom(char *direct, fileheader_t* headers, int recbase, int p_lines, int last_line, int bottom_line) { - int n = bottom_line - recbase + 1, rv; - char directbottom[60]; + int n = bottom_line - recbase + 1, rv; + char directbottom[60]; - if(!last_line) return 0; - if(n>=p_lines || (currmode & (MODE_SELECT | MODE_DIGEST))) - return get_records(direct, headers, sizeof(fileheader_t), recbase, - p_lines); + if( !last_line ) + return 0; + if( n >= p_lines || (currmode & (MODE_SELECT | MODE_DIGEST)) ) + return get_records(direct, headers, sizeof(fileheader_t), recbase, + p_lines); sprintf(directbottom, "%s.bottom", direct); - if (n<=0) - return get_records(directbottom, headers, sizeof(fileheader_t), 1-n, - last_line-recbase + 1); + if( n <= 0 ) + return get_records(directbottom, headers, sizeof(fileheader_t), 1-n, + last_line-recbase + 1); - rv = get_records(direct, headers, sizeof(fileheader_t), recbase, n); + rv = get_records(direct, headers, sizeof(fileheader_t), recbase, n); - if(bottom_line<last_line) - rv += get_records(directbottom, headers+n, sizeof(fileheader_t), 1, - p_lines - n ); - return rv; + if( bottom_line < last_line ) + rv += get_records(directbottom, headers+n, sizeof(fileheader_t), 1, + p_lines - n ); + return rv; } + void -i_read(int cmdmode, char *direct, void (*dotitle) (), void (*doentry) (), onekey_t * rcmdlist, int bidcache) +i_read(int cmdmode, char *direct, void (*dotitle) (), + void (*doentry) (), onekey_t * rcmdlist, int bidcache) { keeploc_t *locmem = NULL; int recbase = 0, mode; @@ -755,11 +767,10 @@ i_read(int cmdmode, char *direct, void (*dotitle) (), void (*doentry) (), onekey case PARTUPDATE: if (last_line < locmem->top_ln + p_lines) { - if (bidcache > 0 && !(currmode & (MODE_SELECT | MODE_DIGEST))) - { - bottom_line = getbtotal(currbid); - num = bottom_line+getbottomtotal(currbid); - } + if (bidcache > 0 && !(currmode & (MODE_SELECT | MODE_DIGEST))){ + bottom_line = getbtotal(currbid); + num = bottom_line+getbottomtotal(currbid); + } else num = get_num_records(currdirect, FHSZ); @@ -785,11 +796,11 @@ i_read(int cmdmode, char *direct, void (*dotitle) (), void (*doentry) (), onekey clrtobot(); case PART_REDRAW: move(3, 0); - if(last_line==0) + if( last_line == 0 ) outs(" 沒有文章..."); else - for (i = 0; i < entries; i++) - (*doentry) (locmem->top_ln + i, &headers[i]); + for( i = 0; i < entries ; i++ ) + (*doentry) (locmem->top_ln + i, &headers[i]); case READ_REDRAW: outmsg(curredit & EDIT_ITEM ? "\033[44m 私人收藏 \033[30;47m 繼續? \033[m" : @@ -808,12 +819,13 @@ i_read(int cmdmode, char *direct, void (*dotitle) (), void (*doentry) (), onekey recbase = 1; locmem->top_ln = recbase; } - entries=get_records_and_bottom(currdirect, - headers, recbase, p_lines, last_line, bottom_line); + entries = + get_records_and_bottom(currdirect, headers, recbase, + p_lines, last_line, bottom_line); } break; } //end switch - mode = i_read_key(rcmdlist, locmem, currbid, bottom_line); + mode = i_read_key(rcmdlist, locmem, currbid, bottom_line); } while (mode != DOQUIT); #undef FHSZ |