C指针原理(35)-Ncurses-文本终端的图形
下面將全屏編輯器修改一下,通過panel的支持,讓它能同時(shí)打開3個(gè)窗口編輯不同的內(nèi)容,同時(shí)對(duì)3個(gè)窗口的內(nèi)容進(jìn)行保存。
效果如下:
#include <locale.h>#include <stdio.h>#include <panel.h>#include <ncurses.h>int isExist(char *filename){return (access(filename, 0) == 0);}int main(int argc, char *argv[]){MEVENT event;setlocale(LC_ALL,"");initscr();clear();noecho();cbreak();if(has_colors() == FALSE){endwin();printf("你的終端不支持色彩!\n");return (1);}start_color(); /啟動(dòng)color 機(jī)制/mvprintw(3,COLS/2-10,"簡(jiǎn)單編輯器-僅限于單個(gè)屏幕的編輯");mvprintw(4,COLS/2-20,"【F9讀保存內(nèi)容,F10存盤,F11退出,F12刪除整行,TAB換窗口】");refresh();init_pair(1, COLOR_GREEN, COLOR_BLACK);init_pair(2, COLOR_BLUE, COLOR_BLACK);init_pair(3, COLOR_RED,COLOR_BLACK); WINDOW *mywins[3];PANEL *top;PANEL *mypanels[3];char filename[10];int width=COLS-18;int height=LINES-18;int x,y;int begin_y=5;int begin_x=5;int i;for(i = 0; i < 3; +++i){mywins[i]=newwin(height,width,begin_y,begin_x);//新窗口(行,列,begin_y,begin_x)keypad(mywins[i],TRUE);wattron(mywins[i],COLOR_PAIR(i+1));mypanels[i] = new_panel(mywins[i]);box(mywins[i],ACS_VLINE,ACS_HLINE);wattroff(mywins[i],COLOR_PAIR(i+1));begin_y+=4;begin_x+=4;}set_panel_userptr(mypanels[0],mypanels[1]);set_panel_userptr(mypanels[1],mypanels[2]);set_panel_userptr(mypanels[2],mypanels[0]);top = mypanels[2];update_panels();doupdate();int nowwinid=2;sprintf(filename,"myed%d.dat",nowwinid);getyx(mywins[nowwinid],y,x);++y;++x;mmask_t oldmousemask;int ans=0;FILE *fp2=NULL;FILE *fp1=NULL;mousemask(ALL_MOUSE_EVENTS, &oldmousemask);while(1){int c=mvwgetch(mywins[nowwinid],y,x);switch(c){ case KEY_MOUSE:if(getmouse(&event) == OK){ / When the user clicks left mouse button /if(event.bstate & BUTTON1_PRESSED){y=event.y-7;x=event.x-7;wmove(mywins[nowwinid],y,x);}}break;case KEY_BACKSPACE:--x;if (x<1){--y;x=width-2;}if (y<1){y=height-2;}mvwprintw(mywins[nowwinid],y,x," ");break;case KEY_RIGHT:++x;if (x>=width-1) {++y;x=1;}break;case KEY_LEFT: --x;if (x<1){--y;x=width-2;}break;case KEY_UP:--y;if (y<1){y=height-2;}break;case KEY_DOWN:++y;if (y>=height-1){y=1;}break;case 10:++y;if (y>=height-1){y=1;}break;case KEY_F(11)://退出mvprintw(LINES-3,2," ");mvprintw(LINES-3,2,"退出編輯器嗎? ");mvprintw(LINES-2,2," ");mvprintw(LINES-1,2," \n");refresh();ans=getch();if (ans=='Y' ||ans=='y'){mvprintw(LINES-2,2,"是\n");refresh();wattroff(mywins[nowwinid],COLOR_PAIR(1));mousemask(oldmousemask,NULL);endwin();return 0;}elsemvprintw(LINES-2,2,"否\n");refresh();break;case 9:top = (PANEL *)panel_userptr(top);top_panel(top);update_panels();doupdate();nowwinid=(++nowwinid)%3;sprintf(filename,"myed%d.dat",nowwinid);break;case KEY_F(10)://存盤mvprintw(LINES-3,2," ");mvprintw(LINES-3,2,"保存當(dāng)前內(nèi)容嗎? ");mvprintw(LINES-2,2," ");mvprintw(LINES-1,2," \n");refresh();ans=getch();if (ans=='Y' ||ans=='y'){mvprintw(LINES-3,2," ");fp1 = fopen(filename,"wb");if (fp1!=NULL){int jg= putwin(mywins[nowwinid],fp1);fclose(fp1);if (jg==OK) mvprintw(LINES-1,2,"保存成功!\n");}mvprintw(LINES-3,2,"保存當(dāng)前內(nèi)容嗎? ");mvprintw(LINES-2,2,"是\n");refresh();}elsemvprintw(LINES-2,2,"否\n");refresh();break;case KEY_F(9)://讀取存盤mvprintw(LINES-3,2," ");mvprintw(LINES-3,2,"讀取保存內(nèi)容嗎? ");mvprintw(LINES-2,2," ");mvprintw(LINES-1,2," \n");refresh();ans=getch();if (ans=='Y' ||ans=='y'){if (isExist(filename)) {fp2 = fopen(filename,"rb");if (fp2!=NULL){WINDOW *newwin=getwin(fp2);if (newwin!=NULL) {WINDOW *temp=mywins[nowwinid];mywins[nowwinid]=newwin;delwin(temp);PANEL *temppan=mypanels[nowwinid];mypanels[nowwinid] = new_panel(mywins[nowwinid]);del_panel(temppan);set_panel_userptr(mypanels[0],mypanels[1]);set_panel_userptr(mypanels[1],mypanels[2]);set_panel_userptr(mypanels[2],mypanels[0]);top = mypanels[nowwinid];top_panel(top);update_panels();doupdate();mvprintw(LINES-1,2,"讀取成功!\n");}fclose(fp2);}}mvprintw(LINES-3,2,"讀取保存內(nèi)容嗎? ");mvprintw(LINES-2,2,"是\n");refresh();}elsemvprintw(LINES-2,2,"否\n");refresh();break;case KEY_F(12)://刪除某行wdeleteln(mywins[nowwinid]);winsertln(mywins[nowwinid]);box(mywins[nowwinid],ACS_VLINE,ACS_HLINE);break;case KEY_DC://刪除某字符mvwprintw(mywins[nowwinid],y,x," ");break;default:mvwprintw(mywins[nowwinid],y,x,"%c",c);++x;if (x>=width-1){++y;x=1;}if (y>=height-1){y=1;}doupdate();}}return 0;}dp@dp:~/cursestest % gcc -lncursesw -lpanel a.c -o mytest
dp@dp:~/cursestest % ./mytest
編寫含有表單的程序,一般步驟如下:
初始化并進(jìn)入curses
用new_field()函數(shù)創(chuàng)建表單域。你可以指定域的高度,寬度以及它在表單中的位
置。
指定已創(chuàng)建的表單域所作用的表單,并用new_form()函數(shù)創(chuàng)建表單。
用post_form()函數(shù)來遞送表單,并刷新屏幕。
用一個(gè)循環(huán)來處理用戶請(qǐng)求,通過form_driver()函數(shù)對(duì)表單做相應(yīng)的更新。
用unpost_form()函數(shù)取消表單的遞送。
用free_form()函數(shù)釋放已分配給表單的內(nèi)存。
用free_field()函數(shù)釋放已分配給菜單項(xiàng)的內(nèi)存。
退出curses 模式
下面演示了表單的操作基礎(chǔ)
#include <form.h>int main(){ FIELD *field[3];FORM *my_form;int ch;/* 初始化curses */initscr();cbreak();noecho();keypad(stdscr, TRUE);/* 初始化表單域*/field[0] = new_field(1, 10, 4, 18, 0, 0);field[1] = new_field(1, 10, 6, 18, 0, 0);field[2] = NULL;/* 設(shè)置表單域*/set_field_back(field[0],A_UNDERLINE); /* 為選項(xiàng)打印一條下滑線*/field_opts_off(field[0],O_AUTOSKIP);/* 在域(輸入框)填滿后光標(biāo)不會(huì)自動(dòng)跳到下一個(gè)表單域*/set_field_back(field[1],A_UNDERLINE);field_opts_off(field[1],O_AUTOSKIP);/* 創(chuàng)建并遞送表單*/my_form = new_form(field);post_form(my_form);refresh();mvprintw(4, 10, "name:");mvprintw(6, 10, "age:");refresh();move(4,15);/* 用循環(huán)獲取用戶請(qǐng)求,F12退出*/while((ch = getch()) != KEY_F(12)){ switch(ch){ case KEY_DOWN:/* 跳至下一個(gè)表單域*/form_driver(my_form,REQ_NEXT_FIELD);/* 跳到當(dāng)前緩沖的末尾*//* 精確地在輸入最后一個(gè)后字符跳出這個(gè)表單域*/form_driver(my_form,REQ_END_LINE);break;case KEY_UP:/* 移動(dòng)到前一個(gè)表單域*/form_driver(my_form,REQ_PREV_FIELD);form_driver(my_form,REQ_END_LINE);break;default:/* 如果輸入的是普通字符, 就把它打印出來*/form_driver(my_form,ch);break;}}/* 取消表單并釋放內(nèi)存*/unpost_form(my_form);free_form(my_form);free_field(field[0]);free_field(field[1]);endwin();return 0;}dp@dp:~/cursestest % gcc -lncursesw -lform b.c -o mytest
dp@dp:~/cursestest % ./mytest
總結(jié)
以上是生活随笔為你收集整理的C指针原理(35)-Ncurses-文本终端的图形的全部?jī)?nèi)容,希望文章能夠幫你解決所遇到的問題。
- 上一篇: Mybatis的xml配置实例
- 下一篇: vue-router进阶:路由使用归纳、