LinuxSir.cn,穿越时空的Linuxsir!

 找回密码
 注册
搜索
热搜: shell linux mysql
查看: 880|回复: 2

curses下实现滚动播报条的练习程序。总是不能正确move到正确坐标。

[复制链接]
发表于 2008-7-5 13:13:56 | 显示全部楼层 |阅读模式
就好象是新闻里的那种滚动的播报条。
我这里的毛病是总是不能move或者mvcur到正确的屏幕坐标。老是从(0,0)开始打印输出。而且擦写功能的坐标也不对。
这是一个用eclipse+Cdt制作的工程。
另外无法使用本论坛附件功能。一点击firefox3.0就停止相应了。

  1. #include <stdio.h>
  2. #include <errno.h>
  3. #include <stdlib.h>
  4. #include <sys/types.h>
  5. #include <sys/stat.h>
  6. #include <fcntl.h>
  7. #include <unistd.h>
  8. #include <stdlib.h>
  9. #include <curses.h>
  10. #include <term.h>
  11. #include <string.h>

  12. #define        MAX_X        50
  13. #define        MAX_Y        50

  14. struct position
  15. {
  16.         int x ;
  17.         int y ;
  18. };

  19. char *get_filled_buff(char *file,int length)
  20. {
  21.         int fd;
  22.         ssize_t reallength;
  23.         char *buff;
  24.         int count;
  25.        
  26.         if(length > 0 &&length < 1024)
  27.         {
  28.                 buff = (char*) malloc(length+1);

  29.                 if(buff == NULL)
  30.                 {
  31.                         perror("buff is  NULL! so kill proccess.\n");
  32.                         exit(1);
  33.                 }
  34.                
  35.         }else
  36.         {
  37.                 perror("length is NOT suitable! so kill proccess.\n");
  38.                 exit(1);
  39.         }
  40.        
  41.         fd = open(file,O_RDONLY);
  42.         if(fd == -1)
  43.         {
  44.                 free(buff);
  45.                 perror("can NOT open the file\n");
  46.                 exit(1);
  47.         }
  48.        
  49.         reallength = read(fd,buff,length);
  50.         if(reallength == -1)
  51.         {
  52.                 close(fd);
  53.                 free(buff);
  54.                 perror("can NOT read the file\n");
  55.                 exit(1);
  56.         }
  57.         for(count=0;count < reallength;count++)
  58.         {
  59.                 if(buff[count] == '\n' ||buff[count] == '\r')
  60.                         buff[count] = ' ';//变成空格
  61.         }
  62.         buff[reallength] = '\0';
  63.        
  64.         close(fd);
  65.        
  66.         return buff;
  67. }

  68. int print_string_with_realx(char* buff,int y,int x,int realy)
  69. {
  70.         int c;
  71.         //clear();
  72.         mvcur(0,0,y,x);
  73.         //refresh();
  74.         for(c        =        0;c        <        realy&&buff[c]        !=        '\0';c++)
  75.         {
  76.                 addch(buff[c]);
  77.         }
  78.        
  79.         refresh();
  80.         //move(x,y);
  81.         return 0;
  82. }

  83. int print_blank_string_with_realx(char* buff,int y,int x,int realy)
  84. {
  85.         int c;
  86.         //clear();
  87.         mvcur(0,0,y,x);
  88.         //refresh();
  89.         for(c        =        0;c        <        realy&&buff[c]        !=        '\0';c++)
  90.         {
  91.                 addch(' ');
  92.         }
  93.        
  94.         refresh();
  95.         //move(x,y);
  96.         return 0;
  97. }

  98. int Theater_Marquee(char *file,int length,int y,int x,int speed)
  99. {
  100.         int c;
  101.         int realy;
  102.         char *buff;
  103.         buff = get_filled_buff(file,length);

  104.         //printf("%s\n",buff);

  105.         initscr() ;               
  106.        
  107.         clear();                       

  108.         //attron(A_BLINK);
  109.        
  110.         for(c        =        0;c        <        MAX_X;c++)
  111.         {
  112.                 realy        =        c+1;//每次实际输出的realx个字符。
  113.                 x        =        MAX_X        -        realy;
  114.                 if(realy >        strlen(buff))
  115.                         break;
  116.                 print_string_with_realx(buff,y,x,realy);
  117.                
  118.                 sleep(1);
  119.                
  120.                 print_blank_string_with_realx(buff,y,x,realy);               
  121.         }
  122.                                
  123.         //attroff(A_BLINK);

  124.         endwin();

  125.         free(buff);
  126.         return 0;
  127. }

  128. int usage()
  129. {
  130.         printf("USAGE(i.e) : ./TheaterMarquee2 -f ./1txt -l 50  -y 30 -s 70000\n(-x is already disabled!)\n");
  131.         exit(0);
  132. }

  133. int main(int ac,char **av)
  134. {
  135.         char *filepath;
  136.         int length;
  137.         struct position position1;
  138.         int speed;
  139.         int c;
  140.        
  141.         if(ac != 9)//这里只是简单的凑服了一下其实不能排除所有的异常情况
  142.         {
  143.                 usage();
  144.         }
  145.        
  146.         while((c=getopt(ac,av,"f:l:y:s:"))!=EOF)  
  147.     {  
  148.                 switch   (c)  
  149.         {  
  150.               case   'f':  
  151.                  filepath        =        optarg;  
  152.             break;  
  153.          case   'l':  
  154.             length        =        atoi(optarg);  
  155.             break;  
  156.          //case   'x':  //其实x系数没有用,起作用的是y系数
  157.             //position1.x        =        atoi(optarg);  
  158.             //break;  
  159.          case   'y':  
  160.             position1.y        =        atoi(optarg);  
  161.             break;  
  162.          case   's':
  163.             speed        =        atoi(optarg);
  164.                  break;
  165.                 default:
  166.                         usage();
  167.                         exit(1);
  168.       }   /*   case   */  
  169.    }  
  170.        
  171.         //printf("%s\n%d\n%d\n%d\n%d\n",filepath,length,position1.x,position1.y,speed);
  172.        
  173.         Theater_Marquee(filepath,length,MAX_Y,MAX_X,speed);//position1.x

  174.         return 0;
  175. }
复制代码
 楼主| 发表于 2008-7-5 21:37:08 | 显示全部楼层

好像传附件可以用了

好像传附件可以用了。不过原来的帖子不能修改了。我传到这个回复里边吧。

本帖子中包含更多资源

您需要 登录 才可以下载或查看,没有帐号?注册

x
回复 支持 反对

使用道具 举报

 楼主| 发表于 2008-7-6 20:40:41 | 显示全部楼层

终于让我解决了!

终于让我解决了!原来是我从笔记本上边做这个练习结果每次分配的边界超出了笔记本特殊的屏幕范围。(25rows*80cols)
重新加上了移动坐标范围的检测代码。并且加了一个自动获取terminfo的函数来获得做大的rows和cols。
  1. #include <stdio.h>
  2. #include <errno.h>
  3. #include <stdlib.h>
  4. #include <sys/types.h>
  5. #include <sys/stat.h>
  6. #include <fcntl.h>
  7. #include <unistd.h>
  8. #include <stdlib.h>
  9. #include <curses.h>
  10. #include <term.h>
  11. #include <string.h>
  12. #include <termios.h>
  13. #include <sys/ioctl.h>

  14. struct position
  15. {
  16.         int x ;
  17.         int y ;
  18. };

  19. int return_winsize(int fd,struct winsize *size)
  20. {
  21.         if(ioctl(fd,TIOCGWINSZ,(char*) size) < 0)
  22.         {
  23.                 perror("iotcl is faild\n");
  24.                 exit(0);
  25.         }
  26.         printf("%d rows,%d colnums\n",size->ws_row,size->ws_col);
  27.         return 0;
  28. }

  29. char *get_filled_buff(char *file,int length)
  30. {
  31.         int fd;
  32.         ssize_t reallength;
  33.         char *buff;
  34.         int count;
  35.        
  36.         if(length > 0 &&length < 1024)
  37.         {
  38.                 buff = (char*) malloc(length+1);

  39.                 if(buff == NULL)
  40.                 {
  41.                         perror("buff is  NULL! so kill proccess.\n");
  42.                         exit(1);
  43.                 }
  44.                
  45.         }else
  46.         {
  47.                 perror("length is NOT suitable! so kill proccess.\n");
  48.                 exit(1);
  49.         }
  50.        
  51.         fd = open(file,O_RDONLY);
  52.         if(fd == -1)
  53.         {
  54.                 free(buff);
  55.                 perror("can NOT open the file\n");
  56.                 exit(1);
  57.         }
  58.        
  59.         reallength = read(fd,buff,length);
  60.         if(reallength == -1)
  61.         {
  62.                 close(fd);
  63.                 free(buff);
  64.                 perror("can NOT read the file\n");
  65.                 exit(1);
  66.         }
  67.         for(count=0;count < reallength;count++)
  68.         {
  69.                 if(buff[count] == '\n' ||buff[count] == '\r')
  70.                         buff[count] = ' ';//变成空格
  71.         }
  72.         buff[reallength] = '\0';
  73.        
  74.         close(fd);
  75.        
  76.         return buff;
  77. }

  78. int print_string_with_realx(char* buff,int y,int x,int realy)
  79. {
  80.         int c;
  81.         if(move(y,x)        ==        ERR)
  82.         {
  83.                 addstr("move ERR\n");
  84.         }       
  85.         for(c        =        0;c        <        realy&&buff[c]        !=        '\0';c++)
  86.         {
  87.                 addch(buff[c]);
  88.         }
  89.         refresh();
  90.         return 0;
  91. }

  92. int print_blank_string_with_realx(char* buff,int y,int x,int realy)
  93. {
  94.         int c;
  95.         if(move(y,x)        ==        ERR)
  96.         {
  97.                 addstr("move blank ERR\n");
  98.         }
  99.         for(c        =        0;c        <        realy&&buff[c]        !=        '\0';c++)
  100.         {
  101.                 addch(' ');
  102.         }
  103.         refresh();
  104.         return 0;
  105. }

  106. int Theater_Marquee(char *file,int length,int y,int x,int speed)
  107. {
  108.         int c;
  109.         int realy;
  110.         int max_x;
  111.         int max_y;
  112.        
  113.         char *buff;
  114.         char *buffpointer;
  115.         buff = get_filled_buff(file,length);
  116.         buffpointer        =        buff;
  117.        
  118.         struct winsize size;
  119.         return_winsize(STDIN_FILENO,&size);
  120.         max_x        =        size.ws_col-10;//80-10
  121.         max_y        =        size.ws_row-5;//25-5
  122.         if(y > max_y)
  123.         {
  124.                 perror("y > max_y\n");
  125.                 exit(1);
  126.         }
  127.         sleep(3);
  128.         //printf("%s\n",buff);

  129.         initscr() ;               
  130.        
  131.         clear();                       

  132.         //attron(A_BLINK);
  133.        
  134.         for(c        =        0;c        <        strlen(buff) ;c++)
  135.         {
  136.                 if(c/max_x<1)
  137.                 {
  138.                         realy        =        c+1;
  139.                         x        =        max_x        -        realy;
  140.                 }
  141.                 else
  142.                 {
  143.                         realy        =        max_x;
  144.                         x        =        0;
  145.                         buff++;
  146.                 }
  147.                 if(realy >        strlen(buff))
  148.                         break;
  149.                        
  150.                 print_string_with_realx(buff,y,x,realy);

  151.                 usleep(speed);
  152.                
  153.                 print_blank_string_with_realx(buff,y,x,realy);               
  154.         }
  155.                                
  156.         //attroff(A_BLINK);

  157.         endwin();

  158.         free(buffpointer);
  159.         return 0;
  160. }

  161. int usage()
  162. {
  163.         printf("USAGE(i.e) : ./TheaterMarquee2 -f ./1txt -l 50  -y 20 -s 70000\n(-x is already disabled!)\n");
  164.         exit(0);
  165. }

  166. int main(int ac,char **av)
  167. {
  168.         char *filepath;
  169.         int length;
  170.         struct position position1;
  171.         int speed;
  172.         int c;
  173.        
  174.         if(ac != 9)//这里只是简单的凑服了一下其实不能排除所有的异常情况
  175.         {
  176.                 usage();
  177.         }
  178.        
  179.         while((c=getopt(ac,av,"f:l:y:s:"))!=EOF)  
  180.     {  
  181.                 switch   (c)  
  182.         {  
  183.               case   'f':  
  184.                  filepath        =        optarg;  
  185.             break;  
  186.          case   'l':  
  187.             length        =        atoi(optarg);  
  188.             break;  
  189.          //case   'x':  //其实x系数没有用,起作用的是y系数
  190.             //position1.x        =        atoi(optarg);  
  191.             //break;  
  192.          case   'y':  
  193.             position1.y        =        atoi(optarg);  
  194.             break;  
  195.          case   's':
  196.             speed        =        atoi(optarg);
  197.                  break;
  198.                 default:
  199.                         usage();
  200.                         exit(1);
  201.       }   /*   case   */  
  202.    }  
  203.        
  204.         //printf("%s\n%d\n%d\n%d\n%d\n",filepath,length,position1.x,position1.y,speed);
  205.        
  206.         Theater_Marquee(filepath,length,position1.y,10,speed);//position1.x

  207.         return 0;
  208. }
复制代码

本帖子中包含更多资源

您需要 登录 才可以下载或查看,没有帐号?注册

x
回复 支持 反对

使用道具 举报

您需要登录后才可以回帖 登录 | 注册

本版积分规则

快速回复 返回顶部 返回列表