`

分享自己写的一个贪吃蛇的游戏(Linux)

阅读更多


作者: dave_cn 发表于 2010-07-18 21:20 原文链接 阅读: 148 评论: 2

转载请注明出处。http://www.cnblogs.com/dave_cn/

本程序需要ncurses库,ubuntu下安装ncurses可以执行下面命令:

sudo apt-get install libncurses5-dev 

关于ncurses的用法,读者可以Google之。

程序运行的效果如下:

其中包含两个窗口,一个为game窗口,一个为日志窗口。 

 

 

 代码如下:

   1 /**

  2  * Snake
  3  * author: dave_cn
  4  * date  : 2010/7/14
  5  * info  :
  6  *        @ ...... food
  7  */
  8 #include <stdio.h>
  9 #include <stdlib.h>
 10 #include <string.h>
 11 #include <sys/time.h>
 12 #include <sys/types.h>
 13 #include <unistd.h>
 14 #include <ncurses.h>
 15 
 16 #define TBool            int
 17 #define True             1
 18 #define False            0    
 19 #define SHAPE_FOOD       '@'
 20 #define SHAPE_SNAKE      '*'
 21 #define GAMEWIN_YLEN     15
 22 #define GAMEWIN_XLEN     60
 23 #define LOGWIN_YLEN      7
 24 #define LOGWIN_XLEN      (GAMEWIN_XLEN)
 25 #define LOGBUF_NUM       (LOGWIN_YLEN-2)
 26 #define LOGBUF_LEN       (GAMEWIN_XLEN-2)
 27 #define MAXLEVEL         12
 28 
 29 #define GetSnakeTail(s)  ((s)->head->front)
 30 
 31 WINDOW *logwin;
 32 #define INITRUNLOG()     logwin = newlogw()
 33 #define RUNLOG(str)      runlog(logwin, str)
 34 #define DESTROYRUNLOG()  delwin(logwin)
 35 
 36 int g_level;
 37 
 38 enum TDirection {
 39     DIR_UP,
 40     DIR_DOWN,
 41     DIR_LEFT,
 42     DIR_RIGHT
 43 };
 44 
 45 struct TFood {
 46     int y;
 47     int x;
 48 };
 49 
 50 struct TSnakeNode {
 51     int y;
 52     int x;
 53     struct TSnakeNode *front;
 54 };
 55 
 56 struct TSnake {
 57     int    length;
 58     struct TSnakeNode *head;
 59     enum   TDirection  dir;
 60 };
 61 
 62 int refreshgamew(WINDOW *win, struct TSnake *psnake);
 63 void movesnake(struct TSnake *psnake);
 64 int checksnake(struct TFood *pfood, struct TSnake *psnake);
 65 void snakegrowup(struct TFood *pfood, struct TSnake *psnake);
 66 void gameover(WINDOW *win, char *str);
 67 struct TSnakeNode *newsnakenode(struct TSnakeNode **ppsnode, int y, int x);
 68 WINDOW* newgamew();
 69 struct TSnake* initsnake();
 70 void destroysnake(struct TSnake *psnake);
 71 void drawsnakew(WINDOW *win, struct TSnake *psnake);
 72 void drawfoodw(WINDOW *win, struct TFood *pfood, struct TSnake *psnake);
 73 TBool checkfood(struct TFood *pfood, struct TSnake *psnake);
 74 WINDOW* newlogw();
 75 void runlog(WINDOW *win, char *str);
 76 void cleanline(WINDOW *win, int y, int x);
 77 
 78 int main()
 79 {
 80     initscr();
 81     raw();
 82     noecho();
 83     keypad(stdscr, TRUE);
 84     curs_set(0);
 85     refresh();
 86 
 87     g_level = 1;
 88     INITRUNLOG();
 89     RUNLOG("  Press 'q' or 'Q' to quit.");
 90     RUNLOG("  Press 'w/s/a/d' or 'W/S/A/D' to move the snake.");
 91     RUNLOG("Info:");
 92     
 93     WINDOW *gwin = newgamew();
 94     struct TSnake *psnake = initsnake();
 95     drawsnakew(gwin, psnake);
 96     
 97     while (refreshgamew(gwin, psnake) >= 0) ;
 98     
 99     getch();
100     
101     destroysnake(psnake);
102     delwin(gwin);
103     DESTROYRUNLOG();
104     endwin();
105     
106     return 0;
107 }
108 
109 int refreshgamew(WINDOW *win, struct TSnake *psnake)
110 {
111     static TBool ffood = False;
112     struct TFood pfood;
113     
114     if (!ffood) {
115         drawfoodw(win, &pfood, psnake);
116         ffood = True;
117     }
118 
119     int key = -1;
120     
121     fd_set set;
122     FD_ZERO(&set);
123     FD_SET(0&set);
124     
125     struct timeval timeout;
126     timeout.tv_sec = 0;
127     timeout.tv_usec= (6 - (int)(g_level/3)) * 100*1000;
128     
129     if (select(1&set, NULL, NULL, &timeout) < 0)
130         return -1;
131     
132     if (FD_ISSET(0&set)) {
133         while ((key = getch()) == -1) ;
134     
135         switch (key) {
136         case 'w':
137         case 'W':
138             (psnake->dir == DIR_DOWN) ? : (psnake->dir = DIR_UP);
139             break;
140         
141         case 's':
142         case 'S':
143             (psnake->dir == DIR_UP) ? : (psnake->dir = DIR_DOWN);
144             break;
145         
146         case 'a':
147         case 'A':
148             (psnake->dir == DIR_RIGHT) ? : (psnake->dir = DIR_LEFT);
149             break;
150         
151         case 'd':
152         case 'D':
153             (psnake->dir == DIR_LEFT) ? : (psnake->dir = DIR_RIGHT);
154             break;
155         
156         case 'q':
157         case 'Q':
158             RUNLOG("Quit Game!");
159             gameover(win, "Quit Game!");
160             return -1;
161         
162         default:
163             break;
164         }
165     }
166 
167     movesnake(psnake);
168     drawsnakew(win, psnake);
169     switch (checksnake(&pfood, psnake)) {
170     case 0:
171         break;
172         
173     case 1:
174         ffood = False;
175         if (++g_level > MAXLEVEL) {
176             RUNLOG("Win!!!");
177             gameover(win, "Win!!!");
178             return -1;
179         }
180         mvwprintw(win, GAMEWIN_YLEN-12" Level: %d ", g_level);
181         mvwprintw(win, GAMEWIN_YLEN-130" Speed: %d ", (int)(g_level/3));
182         wrefresh(win);
183         RUNLOG("Level UP!");
184         snakegrowup(&pfood, psnake);
185         break;
186         
187     default:
188         RUNLOG("Game over!");
189         gameover(win, "Game over!");
190         return -1;
191     }
192     
193     return 1;
194 }
195 
196 /**
197  * stuct TSnake是一个倒置的首尾相连的链表,head->front指向snake的尾部
198  * 如: [a]<-[b]<-[c]<-[d]    a为head
199  *      |              ^     snake移动的时候,只用head指向d,
200  *      `--------------'     并且修改d的(y,x)为snake头移动到的位置.
201  */
202 void movesnake(struct TSnake *psnake)
203 {
204     int hy = psnake->head->y;
205     int hx = psnake->head->x;
206     
207     psnake->head = GetSnakeTail(psnake);
208     
209     switch (psnake->dir) {
210     case DIR_UP:
211         psnake->head->= hy - 1;
212         psnake->head->= hx;
213         break;
214     
215     case DIR_DOWN:
216         psnake->head->= hy + 1;
217         psnake->head->= hx;
218         break;
219     
220     case DIR_LEFT:
221         psnake->head->= hy;
222         psnake->head->= hx - 1;
223         break;
224     
225     case DIR_RIGHT:
226         psnake->head->= hy;
227         psnake->head->= hx + 1;
228         break;
229         
230     default:
231         break;
232     }
233 }
234 
235 int checksnake(struct TFood *pfood, struct TSnake *psnake)
236 {
237     if ( psnake->head-><= 0 || psnake->head->>= GAMEWIN_YLEN
238       || psnake->head-><= 0 || psnake->head->>= GAMEWIN_XLEN)
239     {
240         return -1;
241     }
242 
243     struct TSnakeNode *pnode = GetSnakeTail(psnake);
244     int i = 0;
245     for (; i < psnake->length - 1++i, pnode = pnode->front)
246         if (psnake->head->== pnode->&& psnake->head->== pnode->x)
247             return -1;
248 
249     if (psnake->head->== pfood->&& psnake->head->== pfood->x)
250         return 1;
251     
252     return 0;
253 }
254 
255 void snakegrowup(struct TFood *pfood, struct TSnake *psnake)
256 {
257     struct TSnakeNode *pnode = (struct TSnakeNode *)malloc(sizeof(struct TSnakeNode));
258     
259     switch (psnake->dir) {
260     case DIR_UP:
261         pnode->= psnake->head->- 1;
262         pnode->= psnake->head->x;
263         break;
264     
265     case DIR_DOWN:
266         pnode->= psnake->head->+ 1;
267         pnode->= psnake->head->x;
268         break<sp
分享到:
评论

相关推荐

    基于android贪吃蛇游戏本科(论文).doc

    在本篇基于Android的贪吃蛇游戏本科论文中,作者探讨了如何利用Java语言在Android平台上开发手机游戏,特别是专注于创建一个单机版的贪吃蛇游戏。Android平台是由Google在2007年推出的一个开源系统,它基于Linux内核...

    linux 控制台小游戏

    总的来说,Linux控制台小游戏提供了一个有趣的平台,让我们可以在命令行环境中体验游戏的乐趣,同时也能增进对编程和系统操作的理解。通过分析和修改这些游戏,初学者可以提升自己的编程技能,而资深开发者则能从中...

    brew 贪吃蛇 贪吃蛇的brew代码

    这个压缩包文件的标题提及“brew 贪吃蛇 贪吃蛇的brew代码”,这意味着它包含了一个使用Brew构建的贪吃蛇游戏的源代码。在接下来的内容中,我们将深入探讨Brew的基本概念,以及如何利用Brew来创建和管理自定义软件包...

    贪吃蛇打包(无java环境也能弄个运行)

    在这个场景中,开发者已经成功地将一个Java编写的贪吃蛇游戏进行了打包处理,使得用户在没有Java运行环境的情况下也能运行游戏。 【描述】"贪吃蛇打包成功,无环境也可实现运行的操作"表明了开发者采取了一种技术...

    java毕业设计&课设-俄罗斯方块、贪吃蛇(视频+源码+资料).doc

    - **LibGDX**:一个跨平台的游戏开发框架,支持Windows、Mac、Linux、Android、iOS等多个平台。 - **Slick2D**:基于Java的一个2D游戏开发库,提供了丰富的2D图形处理功能。 - **jMonkeyEngine**:一个面向3D游戏...

    scratch2.0趣味游戏合集.rar

    比如贪吃蛇游戏中,蛇的移动、吃到食物后增长的行为都是通过循环实现的。 2. **变量与数据**:在超级玛丽游戏中,玩家的生命值、分数等信息通常会用到变量来存储和更新。变量是程序中用来储存和传递信息的关键元素...

    嵌入式课程

    在本嵌入式课程设计报告中,学生选择了一个有趣的课题——“贪吃蛇游戏”,以此来实践和提升其在嵌入式系统开发中的技能。 第一章引言部分,学生首先介绍了选题的由来。题目要求是设计并实现一个基于嵌入式系统的...

    MySnakebeat9.rar_android

    Android是一个基于Linux的开源操作系统,广泛应用于智能手机和平板电脑。开发者可能已经对源码进行了调整,使其能够在Android的Dalvik虚拟机上执行。 3. **deployed目录** 这个目录通常包含编译后的二进制文件和...

    LIBerties Of LinuX-开源

    这通常是一个用 C++ 语言编写的源代码文件,可能是一个简单的游戏项目,比如经典的 "贪吃蛇" 游戏。在Linux环境下,开发者经常使用C++这样的编程语言来开发软件,因为Linux提供了丰富的C++开发库和工具,如GCC编译器...

    kde4-ksnakeduel:Knakeduel

    《KDE4-KSnakeDuel:经典游戏的现代演绎》 KDE4-KSnakeDuel,作为一款基于KDE4桌面环境的休闲...无论你是想在空闲时间享受游戏的乐趣,还是希望通过游戏代码深入理解软件开发,KDE4-KSnakeDuel都是一个不错的选择。

    Android教学视频网盘地址

    - **游戏开发**:学习如何利用Android框架编写小游戏,如俄罗斯方块、贪吃蛇等。 ### 学习资源推荐 除了上述提供的教学视频之外,还有许多优质的在线教程和书籍可以帮助初学者快速入门: - **《Head First ...

Global site tag (gtag.js) - Google Analytics