签到

05月06日
尚未签到

共有回帖数 0

    荷塘月色

    等级:
    累死了,5天的心血之作
    #define DEL     263
    #define ENTER     10
    #define UP     259
    #define DOWN     258
    #define LEFT    260
    #define RIGHT    261
    #define COMMAND 58
    #define BUF_SIZE 256
    #define LINE_SIZE 1000
    #define MIN(x,y)   ((x)(y)?(x):(y))

    #include"procerr.h"
    #includecurses.h
    #includestring.h

    char big_mem[10000],buf[BUF_SIZE];
    chtype ch,ch_buf[BUF_SIZE];
    int count[LINE_SIZE];
    bool show=1,save=0,out=0;
    int save_x=0,save_y=0;
    int enter_x,del_x;
    int fd=-1;
    int pad_x=500,pad_y=1000;
    int change_y=0,nread,nwrite,offset=0,cursor_offset=0,line=0;


    WINDOW*pad,*command,*info;

    static void func_step(void);
    static void func_del_ch(void);
    static void func_del_ln(void);

    static void func_enter(void);
    static void func_change_down(void);
    static void func_change_up(void);
    static void func_command(void);

    static void func_text_save(void);
    static void func_pad_save(int);
    static bool func_text_load(void);
    static bool func_pad_load(void);

    static void func_count_line(void);
    static void func_info(void);

    int main(int argc,char*argv[]){

       initscr();    
       noecho();//不回显
       cbreak();//预处理模式
       keypad(stdscr,TRUE);//启用方向健
       refresh();
       raw();//关闭特殊键

       fd=open(argv[1],O_RDWR|O_CREAT,PERM_FILE);    
       func_text_load();
       func_pad_load();
       func_count_line();
       func_info();

       while(1)
           {                      
           switch(ch=getch()){
               case -1:
               case 410:
                   func_pad_load();
                   if(show)func_info();
                   break;    
               case DEL:
                   if(save_x0)
                       {
                       func_del_ch();
                       count[save_y+change_y]--;
                       cursor_offset--;

               func_pad_save(0);
                       if(show)func_info();
                       }
                   else if(save_y0)
                       {
                           int i;    
                           del_x=count[save_y+change_y-1];    
                           count[save_y+change_y-1]+=count[save_y+change_y]-1;
                           for(i=save_y+change_y;iline-1;i++)
                               count=count[i+1];
                           line--;
                       func_del_ln();
                       cursor_offset--;
                       func_pad_save(0);
                       if(show)func_info();    
                       }
                   break;
               case DOWN:
                   if(save_y  LINES-1){
                       cursor_offset+=count[save_y+change_y]-save_x+MIN(count[save_y+change_y+1]-1,save_x);/////////////////////
                       save_y++;
                       wmove(pad,save_y,(save_x=MIN(count[save_y+change_y]-1,save_x)));
                       prefresh(pad,0,0,0,0,LINES-1,COLS-1);            



               }
                   else if(save_y==LINES-1 && (save_y+change_y)  (line-1) ){
                       func_change_down();
                       }
                   if(show)func_info();
                   break;
               case UP:
                   if(save_y0){
                       cursor_offset-=save_x+count[save_y+change_y-1];
                       cursor_offset+=MIN(count[save_y+change_y-1]-1,save_x);

                       save_y--;    
                       wmove(pad,save_y,(save_x=MIN(count[change_y+save_y]-1,save_x)));    
                       prefresh(pad,0,0,0,0,LINES-1,COLS-1);
                       }
                   else if(save_y==0 && change_y0){
                       func_change_up();
                       }
                   if(show)func_info();
                   break;
               case LEFT:
                   if(save_x0){save_x--;func_step();cursor_offset--;}
                   if(show)func_info();
                   break;
               case RIGHT:
                   if(save_xcount[change_y+save_y]-1){save_x++;func_step();cursor_offset++;}
                   if(show)func_info();
                   break;


      case ENTER://不支持卷屏的func_enter
                   func_enter();
                   cursor_offset++;
                   func_pad_save(1);
                   if(show)func_info();
                   break;
               case COMMAND:
                   func_command();
                   if(show)func_info();
                   else func_step();

                   if(save)func_text_save();

                   if(out) goto EXAPLEM_END;

                   break;
               default:
                   winsch(pad,ch);
                   count[save_y+change_y]++;
                   if(save_xCOLS){
                       save_x++;func_step();
                       cursor_offset++;
                       func_pad_save(1);    
                       }
                   else if((save_y+change_y)LINES){
                       save_x=0;save_y++;func_step();//不支持卷屏
                       }
                   if(show)func_info();
                   break;
               }
           }

    EXAPLEM_END:
       noraw();    
       echo();
       nocbreak();
       delwin(pad);

       endwin();
       return 0;
    EC_CLEANUP_BGN
       endwin();
       return 1;
    EC_CLEANUP_END    
    }



    static void func_step()
    {
       wmove(pad,save_y,save_x);
       if(show)prefresh(pad,0,0,0,0,LINES,COLS-5);    
       else prefresh(pad,0,0,0,0,LINES,COLS);
    }

    static void func_del_ch()//offset_end
    {
       save_x--;
       func_step();
       wdelch(pad);
       prefresh(pad,0,0,0,0,LINES-1,COLS-1);

    }

    static void func_del_ln()//offset_end
    {  
       int i=0;
       save_x=COLS-1;
       wmove(pad,save_y,save_x);
       memset(ch_buf,'',BUF_SIZE);
       while(save_x0 && winch(pad)==' '){
               save_x--;
               wmove(pad,save_y,save_x);
                   }
           //准备复制
       buf[save_x+1]='';
       
       for(;save_x=0;){
           ch_buf[save_x]=winch(pad);
           save_x--;
           i++;
           wmove(pad,save_y,save_x);
               }    
           //复制了一个串包含回车
                   
           wdeleteln(pad);
           save_y--;
           save_x=del_x-1;
           wmove(pad,save_y,save_x);

           //准备黏贴
           waddchstr(pad,ch_buf);

           //实施黏贴
           prefresh(pad,0,0,0,0,LINES-1,COLS-1);
       
    }



    static void func_enter(void)                
    {
       int i;
    if(lineLINE_SIZE-1){        
       line++;
       for(i=line-1;isave_y+1;i--)
           count=count[i-1];        
       count[save_y+1]=count[save_y]-save_x;
       count[save_y]=save_x+1;//加了回车    


       enter_x=save_x;
       ch_buf[save_x]='';
       save_x--;
       func_step();
       for(;save_x=0;){
               ch_buf[save_x]=winch(pad);
               save_x--;                
          func_step();
               }                        
       winsertln(pad);
       waddchstr(pad,ch_buf);

       save_y++;                    
       wmove(pad,save_y,(save_x=enter_x));    
       while(save_x0)func_del_ch();
       prefresh(pad,0,0,0,0,LINES-1,COLS-1);
       return;
       }
    else
       return;
    }        


    static void func_command(void)
    {
       int i;
       command=newwin(1,160,LINES-1,0);
       mvwprintw(command,0,0,"command:");
       wmove(command,0,8);
       wrefresh(command);

       for(i=0,enter_x=8;(ch=getch())!='n';i++){
           if(ch==DEL){
               if(enter_x8)enter_x--;
               wmove(command,0,enter_x);
               wdelch(command);
               wrefresh(command);
           }
           else if(ch='a' && ch='z'){
               buf=(char)ch;
               waddch(command,ch);
               enter_x++;
               wmove(command,0,enter_x);
               wrefresh(command);
               }
           }
           buf='';

       if(strcmp(buf,"q")==0) out=1;
       else if(strcmp(buf,"w")==0) save=1;
       else if( strcmp(buf,"wq")==0) out=save=1;
       else if(strcmp(buf,"i")==0) {
           if(show)show--;else show++;
               }
       prefresh(pad,0,0,0,0,LINES-1,COLS-1);
    }
    static void func_pad_save(int add_or_not)
    {
       int i;


       if(add_or_not==1){
           cursor_offset--;

           big_mem[strlen(big_mem)+1]='';
           for(i=strlen(big_mem);icursor_offset;i--)
               big_mem=big_mem[i-1];


           big_mem[cursor_offset]=ch;

           cursor_offset++;
       }
       else{
           for(i=cursor_offset;istrlen(big_mem)-1;i++)
           big_mem=big_mem[i+1];
           big_mem='';
       }


    }


    static void func_text_save(void)//将数组保存到文本之中
    {
       lseek(fd,0,SEEK_SET);
       write(fd,big_mem,strlen(big_mem));
    }
               
    static bool func_text_load(void)
    {
       memset(buf,'',strlen(buf));
       memset(big_mem,'',strlen(big_mem));
       while((nread=read(fd,buf,BUF_SIZE))0){
           strcat(big_mem,buf);            
           memset(buf,'',strlen(buf));
           }

       return 0;
    EC_CLEANUP_BGN
       return -1;
    EC_CLEANUP_END    
    }


    static bool func_pad_load(void)//每次根据cursor_offset来设置光标
    {
       int x,y,off;
       static first=1;
       pad=newpad(LINES,COLS);
       wprintw(pad,"%s",big_mem+offset);
       
       if(first){
           wmove(pad,save_y,save_x);
           prefresh(pad,0,0,0,0,LINES,COLS);
       first=0;
       }
       else{
       off=offset;
       for(y=0;off=cursor_offset;y++)
           off+=count[y+change_y];
           y--;
       off-=count[y+change_y];
       x=cursor_offset-off;    

       save_y=y;
       save_x=x;
       wmove(pad,save_y,save_x);
       prefresh(pad,0,0,0,0,LINES,COLS);
       }
       return 0;
    EC_CLEANUP_BGN
       return -1;
    EC_CLEANUP_END    
    }static void func_change_down(void)
    {
      cursor_offset+=count[save_y+change_y]-save_x+MIN(count[save_y+change_y+1]-1,save_x);/////////////////////

      offset+=count[change_y];

      change_y++;       //BUG
     
      pad=newpad(LINES,COLS);      
      wprintw(pad,"%s",big_mem+offset);
      wmove(pad,save_y,(save_x=MIN(save_x,count[save_y+change_y]-1)));//让其跳到下一行的末尾
      prefresh(pad,0,0,0,0,LINES,COLS);  
    }


    static void func_change_up(void)
    {
      cursor_offset-=save_x+count[save_y+change_y-1];
      cursor_offset+=MIN(count[save_y+change_y-1]-1,save_x);

      change_y--;   //BUG
      offset-=count[change_y];

      pad=newpad(LINES,COLS);      
      wprintw(pad,"%s",big_mem+offset);
      wmove(pad,save_y,save_x);
      prefresh(pad,0,0,0,0,LINES,COLS);  
    }

    static void func_count_line(void) //BUG 如果只有1行并且其中没有n的时候,无法建立count数组,最后一行无法建立
    {
      int i,pre=0,cur=0;
     
      for(i=0;istrlen(big_mem);i++)
          if(big_mem=='n'|| big_mem==''){
              cur=i;
              count[line]=cur-pre+1;
              pre=cur+1;
              line++;
              }
         
    }

    static void func_info()
    {
      int i;
      info=newwin(LINES,8,0,COLS-8);
      mvwprintw(info,0,0,"%d:%d",cursor_offset,count[change_y]);
      for(i=1;iMIN(line,LINES);i++){
          mvwprintw(info,i,0,"%d",count[i+change_y]);
          }
      wrefresh(info);
      wmove(pad,save_y,save_x);
      prefresh(pad,0,0,0,0,LINES,COLS-9);  
     
    }

     


    自己用linux下curses库写的一个文本编辑器,实现了基本的光标操作,del,enter,打开,保存,显示每行长度等功能。有几个BUG - - 写了5天 差点精神崩溃


    楼主 2016-04-15 08:58 回复

共有回帖数 0
  • 回 帖
  • 表情 图片 视频
  • 发表

登录直线网账号

Copyright © 2010~2015 直线网 版权所有,All Rights Reserved.沪ICP备10039589号 意见反馈 | 关于直线 | 版权声明 | 会员须知