C语言贪吃蛇
本文最后更新于7 天前,其中的信息可能已经过时,如有错误请发送评论

前言

有很长一段时间没有发文章了,因为在玩游戏,然后就是做游戏逆向,朋友想搞一个愤怒的小鸟的全通关的破解,然后我废了几天时间帮他做了一个,思路主要是直装(调用so文件,写入全通关存档),然后版本改大,去除更新弹窗,大概花了3,4天,也就是上一篇文章,然后忙完之后又学习了一下C语言

主要是为后续学习逆向打基础,然后学习C语言看的是b站林粒粒的3小时入门C的视频,看完之后又看了黑马程序员的课程,因为我已经有两个语言的学习经历,学习C还是很快的,简单的了解了语法,就一路速通,然后今天已经把结构体学习完毕,因为朋友的教程说是到结构体就够了,所以我也没打算继续看了,然后为了检验学习成果,打算写一个贪吃蛇练练手

我曾经的一个朋友告诉我,当你学习一门语言后想要精进,可以尝试先写个贪吃蛇,当贪吃蛇能够写出来,再去写其他的项目,就更容易得心应手,于是有了这篇文章

代码

#include <stdio.h>
#include <stdlib.h>
#include <windows.h>
#include <conio.h>
#include <time.h>

// 使用宏定义地图宽高
#define map_width 80
#define map_height 25

// 定义墙壁的符号
#define wall '#'

// 定义空地的符号
#define empty ' '

// 定以蛇头的字符
#define Shead '@'

// 定义蛇身的字符
#define Sbody '0'

// 定义食物的字符
#define Sfood '*'

// 使用枚举定义上下左右的整形常量
enum Direction {up,down,left,right};

// 存储地图的二位数组
char GameMap[map_height][map_width];

// 初始化地图
void inItMap() {

    for (int i=0;i < map_height;i++) {
        
        for (int j=0;j < map_width;j++) {
            
            if (i == 0 || i == map_height - 1) {
                GameMap[i][j] = wall;
            }
            else if (j == 0 || j == map_width - 1) {
                GameMap[i][j] = wall;
            }
            else {
                GameMap[i][j] = empty;
            }
        }
    }
}

// 加载地图
void loadingMap() {
    for (int i=0;i<map_height;i++) {

        for (int j=0;j<map_width;j++) {

            printf("%c",GameMap[i][j]);           

        }

        printf("\n");

    }
}

// 定义蛇身的结构体
typedef struct {
    int x;
    int y;
}Body;

// 定义整条蛇
typedef struct {
    Body head;
    Body body[100];
    int len;
    enum Direction dir;
}Snack;

// 定义食物
typedef struct {
    int x;
    int y;
}Food;

// 初始化蛇
void inItSnack(Snack *snack) {
    (*snack).head.x = map_width / 2;
    (*snack).head.y = map_height / 2;
    (*snack).len = 3;
    (*snack).body[0].x = (*snack).head.x;
    (*snack).body[0].y = (*snack).head.y + 1;
    (*snack).body[1].x = (*snack).head.x;
    (*snack).body[1].y = (*snack).head.y + 2;
    (*snack).dir = up;
}

// 画出蛇
void drawSnack(Snack *snack) {
    GameMap[((*snack).head.y)][((*snack).head.x)] = Shead;
    for (int i=0;i <  (((*snack).len) - 1);i++) {
        GameMap[((*snack).body[i].y)][((*snack).body[i].x)] = Sbody;
    }
}

// 移动蛇
void moveSnack(Snack *snack) {

    int oldHeadX = (*snack).head.x;
    int oldHeadY = (*snack).head.y;

    for (int i=((*snack).len-2);i > 0;i--) { 
        (*snack).body[i].x = (*snack).body[i-1].x;
        (*snack).body[i].y = (*snack).body[i-1].y;
    }

    (*snack).body[0].x = oldHeadX;
    (*snack).body[0].y = oldHeadY;


    switch ((*snack).dir) {
        case up:
            (*snack).head.y -= 1;
            break;
        case down:
            (*snack).head.y += 1;
            break;
        case left:
            (*snack).head.x -= 1;
            break;
        case right:
            (*snack).head.x += 1;
            break;
    }
}

// 控制方向
void control(Snack *snack) {
    int res = (_kbhit()) ? (_getch()) : 0;
    res = (res == 224) ? (_getch()) : res;
    int tempDir;
    int current = (*snack).dir;
    switch (res) {
        case 'w':
        case 'W':
        case 72:
            tempDir = up;
            break;
        case 's':
        case 'S':
        case 80:
            tempDir = down;
            break;
        case 'a':
        case 'A':
        case 75:
            tempDir = left;
            break;
        case 'd':
        case 'D':
        case 77:
            tempDir = right;
            break;
        default:
            tempDir = current;
    }
    if (!(
        (current == up    &&  tempDir == down)  || 
        (current == down  &&  tempDir == up)    || 
        (current == left  &&  tempDir == right) || 
        (current == right &&  tempDir == left)  )) 
    {
        (*snack).dir = tempDir;
    }
}

// 生成食物
Food setFood() {
    Food temp;
    temp.x = rand() % (map_width - 2) + 1;
    temp.y = rand() % (map_height - 2) + 1;
    return temp;
}


// 在地图内初始化食物
void inItFood(Food foods[],int len) {
    for (int i=0;i<len;i++) {
        foods[i] = setFood();
    }
}

// 画出食物
void drawfood(Food foods[],int len) {
    
    for (int i=0;i < len;i++) {
        GameMap[foods[i].y][foods[i].x] = Sfood;
    }

}

// 检查食物被吃
void checkEatFood(Snack *snack,Food foods[],int foods_len) {
    for (int i=0;i<foods_len;i++) {
        if (((*snack).head.x == foods[i].x) && ((*snack).head.y == foods[i].y)) 
        {
            (*snack).len += 1;
            foods[i] = setFood();
        }
    }
}

// 检查蛇头是否撞墙
int checkHitWall(Snack *snack) {
    return ((*snack).head.x == 0 || 
            (*snack).head.x == map_width - 1) || 
           ((*snack).head.y == 0 || 
            (*snack).head.y == map_height - 1);
}

// 检查蛇头是否撞到自身
int checkHitSelf(Snack* snack) {
    for (int i=1;i<((*snack).len - 1);i++) {
        if ((((*snack).head.x == (*snack).body[i].x) && ((*snack).head.y == (*snack).body[i].y))) {
            return 1;
        }
    }
    return 0;
}

// 把光标移动到左上角
void gotoTopLeft() {
    HANDLE hout = GetStdHandle(STD_OUTPUT_HANDLE);
    COORD pos = {0,0};
    SetConsoleCursorPosition(hout,pos);
}

// 游戏主入口
int main() {

    srand(time(NULL));

    Snack snack;

    inItSnack(&snack);

    Food foods[20];

    int foods_len = sizeof(foods) / sizeof(Food);

    inItFood(foods,foods_len);

    while(1) {

        inItMap();

        control(&snack);

        checkEatFood(&snack,foods,foods_len);

        moveSnack(&snack);

        if (checkHitWall(&snack) || checkHitSelf(&snack)) {
            puts("Game Over...");
            break;
        }

        drawfood(foods,foods_len);

        drawSnack(&snack);

        gotoTopLeft();

        loadingMap();
        
        Sleep(100);

    }

    return 0;
}

因为没有做过游戏,所以思路方面还是问了几下ai,代码方面都是自己写的,所以可能并不是很完美,但是基本上都没什么问题

文末附加内容
暂无评论

发送评论 编辑评论


				
|´・ω・)ノ
ヾ(≧∇≦*)ゝ
(☆ω☆)
(╯‵□′)╯︵┴─┴
 ̄﹃ ̄
(/ω\)
∠( ᐛ 」∠)_
(๑•̀ㅁ•́ฅ)
→_→
୧(๑•̀⌄•́๑)૭
٩(ˊᗜˋ*)و
(ノ°ο°)ノ
(´இ皿இ`)
⌇●﹏●⌇
(ฅ´ω`ฅ)
(╯°A°)╯︵○○○
φ( ̄∇ ̄o)
ヾ(´・ ・`。)ノ"
( ง ᵒ̌皿ᵒ̌)ง⁼³₌₃
(ó﹏ò。)
Σ(っ °Д °;)っ
( ,,´・ω・)ノ"(´っω・`。)
╮(╯▽╰)╭
o(*////▽////*)q
>﹏<
( ๑´•ω•) "(ㆆᴗㆆ)
😂
😀
😅
😊
🙂
🙃
😌
😍
😘
😜
😝
😏
😒
🙄
😳
😡
😔
😫
😱
😭
💩
👻
🙌
🖕
👍
👫
👬
👭
🌚
🌝
🙈
💊
😶
🙏
🍦
🍉
😣
Source: github.com/k4yt3x/flowerhd
颜文字
Emoji
小恐龙
花!
上一篇