📄 buf_text.hpp
字号:
/* Copyright(c) Ben Bear 2003-2004 */// 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., 59 Temple Place - Suite 330, Boston, MA// 02111-1307, USA.#ifndef __buf_text_hpp#define __buf_text_hpp#include <stdio.h>#include <string.h>#include <ctype.h>class buf_text{public: enum { BUF_BEGIN, BUF_END, BUF_LINE_UP, BUF_LINE_DOWN, BUF_PAGE_UP, BUF_PAGE_DOWN };private: struct buf_line { char *str; bool nl; buf_line *prev; buf_line *next; buf_line () : str(0), nl(false), prev(0), next(0) {} }; buf_line *root_buf; buf_line *tail_buf; int height; int width; int total_lines; int cur_line; buf_line *cur_buf;public: buf_text (const char* text, int h, int w) : root_buf(0), tail_buf(0), height(h), width(w), total_lines(0) { if ((text == 0) || (height <= 0) || (width <= 0)) throw -1; new_text (text); } ~buf_text () { if (root_buf != 0) del_text (); } bool new_text (const char* text); void del_text (); bool set_height (int h) { if (h <= 0) return false; height = h; return true; } bool move (int dir); const char* get_cur_line (); const char* get_bottom_line (); int get_cur_page (const char** page); int get_per () { if (cur_line+height >= total_lines) return 100; else if (cur_line == 0) return -1; int t = total_lines - height; return cur_line * 100 / t; } bool is_cur_nl () { if ((cur_buf != 0) && (cur_buf->nl == true)) return true; else return false; }private: const char* new_line (const char* text, char *buf, int width);};boolbuf_text::new_text (const char* text){ if (root_buf != 0) del_text (); if (text == 0) return false; const char* text_ptr = text; buf_line head_buf; buf_line *last_buf = &head_buf; while (*text_ptr != '\0') { buf_line *tmp_buf = new buf_line; tmp_buf->str = new char[width+1]; tmp_buf->prev = last_buf; last_buf->next = tmp_buf; text_ptr = new_line (text_ptr, tmp_buf->str, width); if (*(text_ptr-1) == '\n') tmp_buf->nl = true; /* printf ("::%s", tmp_buf->str); getchar (); */ last_buf = tmp_buf; ++total_lines; } root_buf = head_buf.next; if (root_buf != 0) { root_buf->prev = 0; tail_buf = last_buf; cur_line = 0; cur_buf = root_buf; } else { tail_buf = 0; cur_line = -1; cur_buf = 0; } return true;}voidbuf_text::del_text (){ buf_line *line = root_buf; while (line != 0) { delete[] line->str; buf_line *tmp = line; line = line->next; delete[] tmp; } root_buf = 0; tail_buf = 0; total_lines = 0; cur_line = -1; cur_buf = 0;}const char*buf_text::new_line (const char* text, char *buf, int width){ if (width <= 0) { *buf = '\0'; return text; } const char* head = text; const char* last_word = text; int cur_w = 0; while ((*text != '\0') && (*text != '\n') && (cur_w < width)) { if (isspace (*text) || iscntrl(*text)) { switch (*text) { case '\t': for (int i = 8 - cur_w % 8; (i > 0) && (cur_w < width); --i) { *buf++ = ' '; ++cur_w; } last_word = text; break; case ' ': *buf++ = ' '; ++cur_w; last_word = text; break; default: // other space or control char, kick break; } } else { *buf++ = *text; ++cur_w; if (!isalnum(*text) && (*text != '_')) last_word = text; } ++text; } if (*text == '\n') ++text; if (isalnum(*text) && isalnum(*(text-1)) // a word been wrap && !(last_word == head)) // the word can wrap { int n = text - (last_word+1); buf -= n; text -= n; } *buf = '\0'; return text;}boolbuf_text::move (int dir){ if (root_buf == 0) return false; switch (dir) { case BUF_BEGIN: cur_line = 0; cur_buf = root_buf; break; case BUF_END: cur_line = total_lines - 1; cur_buf = tail_buf; for (int i = 1; (i < height) && (cur_line > 0); ++i, --cur_line, cur_buf = cur_buf->prev) ; break; case BUF_LINE_UP: if (cur_line == 0) return false; --cur_line; cur_buf = cur_buf->prev; break; case BUF_LINE_DOWN: if (cur_line+height >= total_lines) return false; ++cur_line; cur_buf = cur_buf->next; break; case BUF_PAGE_UP: if (cur_line == 0) return false; for (int i = 0; (i < height) && (cur_line > 0); ++i, --cur_line, cur_buf = cur_buf->prev) ; break; case BUF_PAGE_DOWN: if (cur_line+height >= total_lines) return false; for (int i = 0; (cur_line+height < total_lines) && (i < height); ++i, ++cur_line, cur_buf = cur_buf->next) ; break; default: return false; break; } return true;}const char* buf_text::get_cur_line (){ if (root_buf == 0) return 0; return cur_buf->str;}const char*buf_text::get_bottom_line (){ if (root_buf == 0) return 0; buf_line *buf = cur_buf; for (int i = 1; (i < height) && (buf != 0); ++i, buf = buf->next) ; return buf->str;}intbuf_text::get_cur_page (const char* *page){ if (root_buf == 0) { page[0] = 0; return 0; } buf_line *buf = cur_buf; int i; for (i = 0; (i < height) && (buf != 0); ++i, buf = buf->next) *page++ = buf->str; if (i != height) page[i] = 0; return i;}#endif
⌨️ 快捷键说明
复制代码
Ctrl + C
搜索代码
Ctrl + F
全屏模式
F11
切换主题
Ctrl + Shift + D
显示快捷键
?
增大字号
Ctrl + =
减小字号
Ctrl + -