zoukankan      html  css  js  c++  java
  • easyx图形库做贪吃蛇游戏

    编程总是对着一个黑窗口,可以说是非常乏味了,于是喵喵就翻出来了以前用easyx图形库做图形界面的贪吃蛇游戏。

    不过大家只是当做提高编程的乐趣来学习吧,想进一步做的话可以学习QT,还有其他的框架。

    这是一个easyx图形库的学习教程,建议大家学完再看本文:

    https://www.easyx.cn/skills/List.aspx?id=7

    首先看一下效果图:


    实现的功能:

    基本的吃食物长大,撞墙死亡,特殊食物,游戏暂停,重开游戏,记分数的功能。

    游戏最高分的记录。

    游戏关卡的选择。

    加了游戏的音效,具体的音效,可以在下面下载:

    链接:https://pan.baidu.com/s/1NFn19J7gcXmG45jAuYe4Ig 密码:x5kz

    一些说明:

    这个程序用的基本是C,当时对C++类的理解实在太差,现在也懒的改了。

    这个程序是万恶的VC写的,当时还没发现codeblocks啥的。

    关于程序的功能实现,并不太难,有详细的注释,可以随意复制粘贴。

    下面看贪吃蛇的代码:

    #include "node.h"
    class Food  
    {
    public:
        Food();
        virtual ~Food();
        int food;//0为无食物,1为有食物
        node foodxy;
        int c;//累计出现食物个数
    };
    
    Food::Food()
    {
     c=0;
    }
    
    Food::~Food()
    {
    
    }
    
    class node  
    {
    public:
        int x,y;
        node();
        virtual ~node();
    
    };
    #include "node.h"
    class snake  
    {
    public:
        snake();
        virtual ~snake();
        node jie[200];//蛇每个节点坐标
        int n;//蛇当前节点数
        char dry;//蛇当前前进方向
    };
    class wall  
    {
    public:
        node dry[30];//障碍物的坐标
        int n;//障碍物的个数
        wall();
        virtual ~wall();
    
    };
      1 #include<graphics.h>
      2 #include<conio.h>
      3 #include<time.h>
      4 #include "snake.h"
      5 #include "Food.h"
      6 #include<stdio.h>
      7 #include<fstream.h>
      8 #include "mmsystem.h"//导入声音头文件 
      9 #pragma comment(lib,"winmm.lib")//导入声音头文件库 
     10 #include "wall.h"
     11 int wallnum,speed;
     12 
     13 void zero();
     14 void first();//操作页面初始化
     15 int second( Food &, snake&);//数据初始化
     16 void foodstyle(Food&,wall);//食物状态
     17 void gameover(snake,int);//游戏结束
     18 void judge( Food&,snake&,int,wall);//判断游戏是否结束
     19 void judge2(Food &,snake&);//判断蛇是否吃到食物
     20 void snakemove(Food&,snake&,wall);
     21 void snakeshow(Food &,snake &,wall);
     22 void change(Food &,snake &,int);//改变方向
     23 void score(snake );//记录分数
     24 void wallstyle(wall&);//障碍物的状态
     25 
     26 
     27 int main()
     28 {
     29     initgraph(640,560);
     30     int o;
     31     Food F;
     32     snake Snake;
     33     wall Wall;
     34     first();
     35     zero();    
     36   o= second(F,Snake);
     37    wallstyle(Wall);
     38 PlaySound("kaichang.wav",NULL,SND_FILENAME|SND_ASYNC);//载入声音特效
     39     while(1)
     40     {
     41         while(!kbhit())//没有键盘输入时
     42         {
     43     
     44     if(!F.food )
     45     {
     46     foodstyle(F,Wall);
     47     }
     48     judge(F,Snake,o,Wall);
     49     judge2(F,Snake);
     50     snakemove(F,Snake,Wall);
     51     Sleep(speed);//控制速度
     52     score(Snake);
     53         }
     54         change(F,Snake,o);
     55         
     56     }
     57     return 0;
     58 }
     59 
     60 void zero()
     61 {
     62     char p[1];
     63     outtextxy(490,30,_T("关卡:"));
     64     for(int i=0;i<3;i++)
     65     {
     66     RECT r= {520+40*i,35,560+40*i,45};//使数字显示在矩形区域中央
     67     sprintf(p, "%d", i+1);
     68     drawtext(p, &r, DT_CENTER | DT_VCENTER | DT_SINGLELINE);
     69     }
     70     settextstyle(40, 15, _T("黑体"));
     71     outtextxy(50,200,_T("请输入 1 or 2 or 3  确定关卡"));
     72     char c=getch();//控制选择关卡
     73     switch (c)
     74     {
     75     case '1':
     76         wallnum=10;
     77         speed=300;
     78         i=1;
     79         break; 
     80     case '2':
     81         wallnum=15;
     82         speed=200;
     83         i=2;
     84         break; 
     85     case '3':
     86         wallnum=15;
     87         speed=100;    
     88         i=3;
     89         break;
     90     default:
     91         settextcolor(BLACK);//擦除
     92         outtextxy(50,200,_T("请输入 1 or 2 or 3  确定关卡"));
     93         settextcolor(RED);
     94         outtextxy(200,200,_T("请正确输入"));
     95         Sleep(1000);//确保显示时间
     96         main();
     97 }
     98     setfillcolor(GREEN);
     99     RECT v= {530+40*(i-1),20,550+40*(i-1),60};
    100     sprintf(p, "%d", i);
    101     drawtext(p, &v, DT_CENTER | DT_VCENTER | DT_SINGLELINE);
    102     settextcolor(BLACK);
    103     outtextxy(50,200,_T("请输入 1 or 2 or 3  确定关卡"));
    104     settextcolor(RED);//确保以后的字体颜色
    105 }
    106 void first()
    107 {
    108     srand((unsigned)time(NULL));//播种子
    109     setlinestyle(PS_DASH);//实线
    110     settextcolor(RED);
    111     setlinecolor(BLUE);
    112     line(480,0,480,480);//分界线
    113     line(0,480,640,480);
    114     outtextxy(490,90,_T("分数:"));//操作说明
    115     outtextxy(490,150,_T("最高分:"));
    116     outtextxy(490,210,_T("操作方式:"));
    117     outtextxy(490,260,_T(" W/w:上移  S/s:下移"));
    118     outtextxy(490,310,_T(" A/a:左移   D/d:右移"));
    119     outtextxy(490,360,_T("    空格:暂停/开始"));
    120     outtextxy(490,410,_T("         Esc:退出"));
    121     outtextxy(490,450,_T("       作者:丁喵喵"));
    122     setlinecolor(BLUE);//示例图形
    123     setfillcolor(GREEN);
    124     fillcircle(310,495,10);
    125     fillcircle(30,535,5);
    126     setfillcolor(RED);
    127     fillrectangle(20,505,40,525);
    128     fillrectangle(300,510,320,530);
    129     setfillcolor(BLACK);
    130     fillcircle(310,520,10);
    131     outtextxy(20,490,_T("温馨提示:"));
    132     outtextxy(50,510,_T("一.障碍物,撞击死亡"));
    133     outtextxy(320,510,_T("四.被破坏障碍物,非无敌状态撞击仍会死亡"));
    134     outtextxy(50,530,_T("二.特殊食物,吃掉冲撞障碍物不死亡"));
    135     outtextxy(320,490,_T("三.蛇吃完特殊食物后的无敌状态"));
    136     outtextxy(320,530,_T("五.只有蛇头时冲撞障碍物不死亡"));
    137 }
    138 
    139 int second(Food & F,snake & Snake)
    140 {
    141     F.food=0;//食物有无、蛇结束、位置、前进方向初始化
    142     Snake.n=1;
    143     Snake.jie[0].x=40;
    144     Snake.jie[0].y=40;
    145     setfillcolor(RED);
    146     fillcircle( Snake.jie[0].x,Snake.jie[0].y,10);
    147     Snake.dry='d';
    148     ifstream inFile("scoremax.txt",ios::in);//读入文件
    149     int o;
    150     inFile>>o;
    151     char p[1];
    152     sprintf(p, "%d", o);
    153     settextstyle(10, 10, _T("黑体"));
    154     outtextxy(550,150,p);//最高分
    155     sprintf(p, "%d", (Snake.n-1)*10);
    156     outtextxy(550,90,p);//分数
    157     return o;
    158 }
    159 
    160 void foodstyle(Food & F,wall Wall)
    161 {
    162 if(!F.food)
    163    {
    164     F.foodxy.x=(rand()%22)*20+20;//食物出现地点
    165     F.foodxy.y=(rand()%22)*20+20;
    166     //确保食物不出现在障碍物及蛇初始位置
    167     while((F.foodxy.x==40&&F.foodxy.y==40)||(F.foodxy.x==60&&F.foodxy.y==40))
    168     {
    169     F.foodxy.x=(rand()%22)*20+20;
    170     F.foodxy.y=(rand()%22)*20+20;
    171     }
    172     for(int i=0;i<Wall.n;i++)
    173     {
    174         if(F.foodxy.x==Wall.dry[i].x&&F.foodxy.y==Wall.dry[i].y)
    175         {
    176             foodstyle(F,Wall);
    177         }
    178     }
    179 setlinestyle(PS_SOLID);
    180 if((F.c+1)%5==0&&(F.c+1)!=0)//判断是否为特殊食物
    181     {
    182     setfillcolor(GREEN);
    183     }
    184     else
    185     {
    186     setfillcolor(YELLOW);
    187     }
    188 fillcircle(F.foodxy.x,F.foodxy.y,5);
    189     F.food=1;//食物状态为有
    190     F.c++;//累计出现食物个数
    191 }
    192 }
    193 void judge(Food & F,snake & Snake,int o,wall Wall)
    194 {
    195     if(Snake.jie[0].x<=0||Snake.jie[0].x>=480||Snake.jie[0].y<=0||Snake.jie[0].y>=480)
    196     {//判断是否撞墙
    197         PlaySound("zhuangqiang.wav",NULL,SND_FILENAME|SND_ASYNC);
    198         Sleep(3000);
    199         gameover(Snake,o);
    200     }
    201     for(int i=1;i<=Snake.n;i++)
    202     {//判断是否咬到自己
    203     if(Snake.jie[0].x==Snake.jie[i].x&&Snake.jie[0].y==Snake.jie[i].y)
    204     {
    205         PlaySound("yao.wav",NULL,SND_FILENAME|SND_ASYNC);
    206         Sleep(3000);
    207         gameover(Snake,o);
    208     }
    209     }
    210     for(i=0;i<Wall.n;i++)
    211     {//判断是否撞到障碍物
    212       if(Snake.jie[0].x<Wall.dry[i].x+20&&Snake.jie[0].y<Wall.dry[i].y+20&&
    213           Snake.jie[0].x>Wall.dry[i].x-20&&Snake.jie[0].y>Wall.dry[i].y-20)
    214       {
    215           if((F.c-1)%5!=0&&F.c!=1)//非无敌状态
    216           {
    217           PlaySound("zhuangqiang.wav",NULL,SND_FILENAME|SND_ASYNC);
    218           Sleep(3000);
    219           gameover(Snake,o);
    220           }
    221       }
    222     }
    223     
    224 }
    225 
    226 void judge2(Food & F,snake & Snake)
    227 {
    228     if(Snake.jie[0].x==F.foodxy.x&&Snake.jie[0].y==F.foodxy.y)//判断是否吃到食物
    229     {
    230     PlaySound("shiwu.wav",NULL,SND_FILENAME|SND_ASYNC);
    231     setfillcolor(BLACK);//擦除
    232     fillcircle(F.foodxy.x,F.foodxy.y,5);
    233     Snake.n++;//蛇结数增加
    234     setfillcolor(BLUE);
    235     fillcircle( F.foodxy.x,F.foodxy.y,10);
    236     F.food=0;//食物被吃掉
    237     }
    238 }
    239 void gameover(snake  Snake,int o)
    240 {
    241     if(o<=(Snake.n-1)*10)//判断是否需要更改最高分
    242     {
    243     PlaySound("zhangsheng.wav",NULL,SND_FILENAME|SND_ASYNC);
    244     ofstream outFile("scoremax.txt",ios::out);//写入文件
    245     outFile<<(Snake.n-1)*10;
    246     outFile.close();
    247     } 
    248     else
    249     {
    250      PlaySound("Game_over.wav",NULL,SND_FILENAME|SND_ASYNC);
    251     }
    252     settextcolor(RED);
    253     settextstyle(180, 40, _T("黑体"));
    254     outtextxy(100,100,_T("GAME OVER"));
    255     settextstyle(40, 15, _T("黑体"));
    256     outtextxy(200,300,_T("是否重新开始"));
    257     outtextxy(150,350,_T("YES(Y/y)"));
    258     outtextxy(350,350,_T("NO(N/n)"));
    259     char c=getch();//判断是否重新开始
    260     if(c=='n'||c=='N')
    261     {
    262     closegraph();//关闭画布    
    263     }
    264     else if(c=='y'||c=='Y')
    265     {
    266       main();
    267     }
    268     else//避免输入移动指令破坏画面
    269     {
    270         gameover(Snake,o);
    271     }
    272 
    273 }
    274 
    275 void snakemove(Food & F,snake & Snake,wall Wall)
    276 {
    277   int i; 
    278   for (i=Snake.n ; i>0; i--)//蛇身每一节移到前一节位置
    279     {
    280         Snake.jie[i].x = Snake.jie[i-1].x;
    281         Snake.jie[i].y = Snake.jie[i-1].y;
    282     } 
    283     switch (Snake.dry)//判断之前的移动方向 蛇头并按该方向移到
    284     {
    285     case 'W':
    286     case 'w':
    287         Snake.jie[0].y-=20;
    288         break; 
    289     case 's':
    290     case 'S':
    291         Snake.jie[0].y +=20;
    292         break;
    293     case 'A':
    294     case 'a':
    295         Snake.jie[0].x -=20;
    296         break;
    297     case 'D':
    298     case 'd':
    299         Snake.jie[0].x +=20;
    300         break;
    301     };
    302     snakeshow(F,Snake,Wall);//将结果显示
    303 }
    304 
    305 void change(Food & F,snake & Snake,int o)
    306 {
    307     char key,p[1];
    308     IMAGE tmp;
    309     int i;
    310     key = getch();
    311     switch (key)
    312     {
    313         case 'w':
    314         case 'W':
    315             if (Snake.dry !='s'&&Snake.dry !='S')//确保不反向移动
    316             {
    317                 Snake.dry ='w';
    318             }
    319             break;
    320         case 's':
    321         case 'S':
    322             if (Snake.dry !='w'&&Snake.dry !='W')
    323             {
    324                 Snake.dry = 's';
    325             }
    326             break;
    327         case 'a':
    328         case 'A':
    329             if (Snake.dry !='D'&&Snake.dry !='d')
    330             {
    331                 Snake.dry = 'a';
    332             }
    333             break;
    334         case 'd':
    335         case 'D':
    336             if (Snake.dry !='a'&&Snake.dry !='A')
    337             {
    338                 Snake.dry = 'd';
    339             }
    340             break;
    341         case' '://暂停
    342            
    343             getimage(&tmp,150,200,150,40);//将该区域图像保存
    344             settextstyle(40, 15, _T("黑体"));
    345             outtextxy(150, 200, _T("任意键继续")); 
    346             PlaySound("stop.wav",NULL,SND_FILENAME|SND_ASYNC);
    347             getch();
    348             putimage(150,200,&tmp);//将保存图像返回,确保不破坏背景
    349             for(i=3;i>=1;i--)//倒计时
    350             {
    351             settextstyle(40, 15, _T("黑体"));
    352             sprintf(p, "%d", i);
    353             outtextxy(200, 200, p);
    354             Sleep(1000);
    355             putimage(150,200,&tmp);
    356             }
    357             PlaySound("start.wav",NULL,SND_FILENAME|SND_ASYNC);
    358             break;
    359         case 27:
    360             gameover(Snake,o);//退出
    361             break;
    362     }
    363 }
    364 
    365 void snakeshow(Food & F,snake & Snake,wall Wall)
    366 {
    367 int i; 
    368     for (i=Snake.n-1; i>0; i--)//蛇身
    369     {
    370         setfillcolor(BLUE); 
    371         fillcircle( Snake.jie[i].x,Snake.jie[i].y,10);
    372     } 
    373     if((F.c-1)%5==0&&F.c!=1)//特殊食物
    374     {
    375         setfillcolor(GREEN);
    376     }
    377     else
    378     {
    379         setfillcolor(RED);
    380     }
    381         fillcircle( Snake.jie[0].x,Snake.jie[0].y,10);
    382         setlinecolor(BLACK);
    383         setfillcolor(BLACK);//擦除之前最后一节蛇身
    384         fillcircle( Snake.jie[Snake.n].x,Snake.jie[Snake.n].y,10);
    385         if(Snake.n>1)
    386         {
    387             setfillcolor(BLUE);
    388         }
    389         else
    390         {
    391             setfillcolor(RED);
    392         }
    393     fillcircle( Snake.jie[Snake.n-1].x,Snake.jie[Snake.n-1].y,10);
    394 } 
    395 
    396 
    397 void score(snake  Snake)
    398 {
    399     char p[1];
    400     sprintf(p, "%d", (Snake.n-2)*10);
    401     settextcolor(BLACK);
    402     outtextxy(550,90,p);
    403     sprintf(p, "%d", (Snake.n-1)*10);
    404     settextcolor(RED);
    405     settextstyle(10, 10, _T("黑体"));
    406     outtextxy(550,90,p);
    407 
    408 }
    409 
    410 void wallstyle(wall & Wall)
    411 {
    412     Wall.n =wallnum;
    413     for(int i=0;i<Wall.n;i++)
    414     {
    415     Wall.dry[i].x=(rand()%22)*20+20;//障碍物出现地点
    416     Wall.dry[i].y=(rand()%22)*20+20;
    417     while((Wall.dry[i].x==40&&Wall.dry[i].y==40)||(Wall.dry[i].x==60&&Wall.dry[i].y==40)
    418         ||(Wall.dry[i].x==80&&Wall.dry[i].y==40))
    419     {
    420         Wall.dry[i].x=(rand()%22)*20+20;//障碍物出现地点
    421         Wall.dry[i].y=(rand()%22)*20+20;
    422     }
    423     setfillcolor(RED);
    424     fillrectangle(Wall.dry[i].x-10,Wall.dry[i].y-10,Wall.dry[i].x+10,Wall.dry[i].y+10);
    425     for(int j=0;j<i;j++)//确保障碍物不重叠
    426     {
    427         if(Wall.dry[i].x==Wall.dry[j].x&&Wall.dry[i].y==Wall.dry[j].y)
    428         {
    429             i--;
    430         }
    431     }
    432     }   
    433 }
  • 相关阅读:
    中文词频统计
    复合数据类型,英文词频统计
    Mybatis 异常:Cause: java.io.IOException: Could not find resource com.xxx.xxx.xml
    Ajax:修改了项目的ajax相关代码,点击运行没有效果
    大数据应用期末总评
    分布式并行计算MapReduce
    分布式文件系统HDFS 练习
    安装关系型数据库MySQL和大数据处理框架Hadoop
    爬虫综合大作业
    爬取全部的校园新闻
  • 原文地址:https://www.cnblogs.com/dingruihfut/p/9326083.html
Copyright © 2011-2022 走看看