在unxi/linux编程实践第七章的基础上完成的一个小的终端弹球游戏,先来个截图。
这个小游戏用到了以下几个知识点:
mybounce.c
#include <stdio.h>
#include <curses.h>
#include <signal.h>
#include "mybounce.h"
#include <termios.h>
#include <sys/time.h>
struct ppball the_ball ;
/** the main loop **/
void set_up();
void wrap_up();
int downedge1=15,downedge2=29;
bool game_over_flag=false;
static struct termios info;
int main()
{
int c;
printf("\033[?25l");
set_up();
while ( ( c = getchar()) != 'q' ){
//if ( c == 'f' ) the_ball.x_ttm--;
//else if ( c == 's' ) the_ball.x_ttm++;
//else if ( c == 'F' ) the_ball.y_ttm--;
//else if ( c == 'S' ) the_ball.y_ttm++;
if ( c == 'f' ){
the_ball.x_ttm--;
the_ball.y_ttm--;
}else if(c=='s'){
the_ball.x_ttm++;
the_ball.y_ttm++;
}else if(c=='z'){
if(game_over_flag){
wrap_words(10,32,15);
wrap_words(11,27,29);
refresh();
move(999,999);
set_up();
}
}else if(c=='j'){
if(downedge1>11){
mvaddch(20,downedge2,' ');
downedge1--;
downedge2--;
}
}else if(c=='k'){
if(downedge2<69){
mvaddch(20,downedge1,' ');
downedge1++;
downedge2++;
}
}
}
wrap_up();
yesecho();
}
void wrap_words(int x,int y,int num_space){
int i=0;
for(i=0;i<num_space;i++){
move(x,y+i);
addch(' ');
refresh();
}
}
int noecho(){
if(tcgetattr(0,&info)==-1){
perror("tcgettattr");
exit(1);
}
info.c_lflag &= ~ECHO;
if(tcsetattr(0,TCSANOW,&info)){
perror("setattr error");
exit(1);
}
}
void yesecho(){
info.c_lflag&= ECHO;
if(tcsetattr(0,TCSANOW,&info)){
perror("setattr error");
exit(1);
}
}
void set_up()
/*
* init structure and other stuff
*/
{
void ball_move(int);
the_ball.y_pos = Y_INIT;
the_ball.x_pos = X_INIT;
the_ball.y_ttg = the_ball.y_ttm = Y_TTM ;
the_ball.x_ttg = the_ball.x_ttm = X_TTM ;
the_ball.y_dir = 1 ;
the_ball.x_dir = 1 ;
the_ball.symbol = DFL_SYMBOL ;
initscr();
noecho();
crmode();
signal( SIGINT , SIG_IGN );
mvaddch( the_ball.y_pos, the_ball.x_pos, the_ball.symbol );
paintedge();
paintline();
noecho();
refresh();
signal( SIGALRM, ball_move );
set_ticker( 1000 / TICKS_PER_SEC ); /* send millisecs per tick */
}
void paintedge(){
move(4,9);
addstr("---------------------------------------------------------------");
int i=0;
for(i=5;i<=20;i++){
move(i,9);
addstr("|");
}
for(i=5;i<=20;i++){
move(i,71);
addstr("|");
}
}
void paintline(){
for(int i=downedge1;i<=downedge2;i++){
move(20,i);
addch('_');
}
move(999,999);
refresh();
}
void wrap_up()
{
set_ticker( 0 );
endwin(); /* put back to normal */
}
void ball_move(int signum)
{
int y_cur, x_cur, moved;
paintline();
signal( SIGALRM , SIG_IGN ); /* dont get caught now */
y_cur = the_ball.y_pos ; /* old spot */
x_cur = the_ball.x_pos ;
moved = 0 ;
if ( the_ball.y_ttm > 0 && the_ball.y_ttg-- == 1 ){
the_ball.y_pos += the_ball.y_dir ; /* move */
the_ball.y_ttg = the_ball.y_ttm ; /* reset*/
moved = 1;
}
if ( the_ball.x_ttm > 0 && the_ball.x_ttg-- == 1 ){
the_ball.x_pos += the_ball.x_dir ; /* move */
the_ball.x_ttg = the_ball.x_ttm ; /* reset*/
moved = 1;
}
if ( moved ){
mvaddch( y_cur, x_cur, BLANK );
mvaddch( y_cur, x_cur, BLANK );
mvaddch( the_ball.y_pos, the_ball.x_pos, the_ball.symbol );
bounce_or_lose( &the_ball );
move(LINES-1,COLS-1);
refresh();
}
signal( SIGALRM, ball_move); /* for unreliable systems */
}
int bounce_or_lose(struct ppball *bp)
{
int return_val = 0 ;
if ( bp->y_pos == TOP_ROW ){
bp->y_dir = 1 ;
return_val = 1 ;
} else if ( bp->y_pos == BOT_ROW ){
if(bp->x_pos>=downedge1 && bp->x_pos<=downedge2){
bp->y_dir = -1 ;
return_val = 1;
paintline();
refresh();
}else{
set_ticker(1000000000);
move(10,32);
addstr("---GAME OVER---");
move(11,27);
addstr("you can press 'z',paly again.");
refresh();
game_over_flag=true;
}
}
if ( bp->x_pos == LEFT_EDGE ){
bp->x_dir = 1 ;
return_val = 1 ;
} else if ( bp->x_pos == RIGHT_EDGE ){
bp->x_dir = -1;
return_val = 1;
}
return return_val;
}
set_ticker( n_msecs )
{
struct itimerval new_timeset;
long n_sec, n_usecs;
n_sec = n_msecs / 1000 ;
n_usecs = ( n_msecs % 1000 ) * 1000L ;
new_timeset.it_interval.tv_sec = n_sec; /* set reload */
new_timeset.it_interval.tv_usec = n_usecs; /* new ticker value */
new_timeset.it_value.tv_sec = n_sec ; /* store this */
new_timeset.it_value.tv_usec = n_usecs ; /* and this */
return setitimer(ITIMER_REAL, &new_timeset, NULL);
}
mybounce.h
/* bounce.h */
/* some settings for the game */
#define BLANK ' '
#define DFL_SYMBOL 'o'
#define TOP_ROW 5
#define BOT_ROW 20
#define LEFT_EDGE 10
#define RIGHT_EDGE 70
#define X_INIT 10 /* starting col */
#define Y_INIT 10 /* starting row */
#define TICKS_PER_SEC 50 /* affects speed */
#define X_TTM 5
#define Y_TTM 8
/** the ping pong ball **/
struct ppball {
int y_pos, x_pos,
y_ttm, x_ttm,
y_ttg, x_ttg,
y_dir, x_dir;
char symbol ;
} ;
欢迎与我分享你的看法。 转载请注明出处:http://taowusheng.cn/