• 终端弹球设计和时钟滴答

    2008-05-09

    版权声明:转载时请以超链接形式标明文章原始出处和作者信息及本声明
    http://peterpannju.blogbus.com/logs/20560824.html

        这是 linux 课程实践的大作业:
           用 curses 库实现终端弹球游戏。

        本身程序设计没有什么困难的,curses 库的使用在 google 上一搜一大把,《Beginning Linux Programming》和《Understanding Unix/Linux Programming》两本书上都有比较详细的介绍,其中后者甚至就以弹球游戏作为例子。令我差异的是,《APUE》上反而对 curses 库一笔带过,甚至连介绍 API 都没有。
        由此可见,curses 库已经落后于时代,在这个 X 桌面系统横行的时期,curses, 还是一边凉快去吧。
        所以,我只是一笔带过,把主要篇幅置于“如何设置定时器”上。

        CSDN 上有人一语道破天机,所谓设置定时器,过程就是“安装一个 SIGALARM 的信号处理函数”。
        其实还是有两个步骤的:
           1. 使用 setitimer() 系统调用让系统每隔一定时钟滴答就发出一个 SIGALARM 信号;
           2. 注册处理 SIGALARM 信号的处理函数;
        相关数据结构和 API 如下:

    #include <sys/time.h>

    /* 设置时钟频率(原先存于 value 数据结构中) */
    int setitimer (int which, const struct itimerval *value, struct itimerval *ovalue);

    struct itimerval {
      struct timeval it_interval; /* next value */
      struct timeval it_value; /* current value */
    };
    struct timeval {
      long tv_sec; /* seconds */
      long tv_usec; /* microseconds */
    };
        而我程序中相关代码块如下:

    /* 设置信号处理函数 move_ball() */
    signal(SIGALRM,move_ball);
      
    /* 调用定时器设置函数 set_ticker() */
    set_ticker(20);

    void set_ticker(int msec)
    {
      struct itimerval ntimerset;
      long sec,usec;
      sec=msec/1000;
      usec=(msec%1000)*1000L;
      ntimerset.it_value.tv_sec=sec;
      ntimerset.it_value.tv_usec=usec;
      ntimerset.it_interval.tv_sec=sec;
      ntimerset.it_interval.tv_usec=usec;
      //时钟滴答开始啦
      setitimer(ITIMER_REAL,&ntimerset,NULL);
    }
        这样,在 SIGALARM 的处理函数中刷新屏幕,就可以让小球动起来。
     

     


    收藏到:Del.icio.us




    评论

  • setitimer 函数调用是否会使该进程的时间颗粒度变粗?