目录
目录
游戏简介
准备素材
开始编写
1 预编译
2 字母结构体
3 初始化字母
4 字母下落
不断下落
掉到底下
MoveLetter() 函数
5 绘制屏幕
字母
分数
Draw() 函数
6 判断按键
7 音乐、背景
音乐
背景
Main函数
效果截图
完整代码
游戏简介
屏幕中不断下落字母,判断按下这个字母的按键,得分;字母掉下去,扣分。
上面这句话中,我们要给蓝色背景的字定义一个结构体,然后一步步实现红色字的内容。
代码思路
1. 字母结构体
2. 初始化字母
3. 字母下落(到底失分)
4. 绘制屏幕
5. 判断按键(得分)
6. 音乐、背景(可加可不加)
准备素材
背景图:
(偷偷说一件事:我的这些背景图,都是在 Scratch 上截的)
音效也是在 Scratch 上导出的……
开始编写
1 预编译
#include <stdio.h>#include <graphics.h>#include <conio.h>#include <time.h>#include <mmsystem.h>#pragma comment(lib, "winmm.lib") // 音乐#define WIDTH 640#define HEIGHT 480#define MAX_LETTER 10#define SPEED 2
2 字母结构体
xx坐标
yy坐标
speed下落速度
ch 字母
struct Letter{int x;int y;char ch;};
3 初始化字母
定义宏MAX_LETTER表示字母的数量。
定义letter[MAX_LETTER]表示所有字母的一维数组。
Letter letter[MAX_LETTER];
x坐标:25 ~ 615 的随机数
y坐标:-480 ~ 0 的随机数
字母:利用 ASCII码 取 A ~ Z 的随机数
// 初始化字母void SetLetter(){for (int i = 0; i < MAX_LETTER; i++){letter[i].x = rand() % (WIDTH - 50) + 25;letter[i].y = rand() % HEIGHT - HEIGHT;letter[i].ch = rand() % 26 + 'A';}}
4 字母下落
不断下落
只要增加每个字母的y坐标就行了。
for (int i = 0; i < MAX_LETTER; i++){letter[i].y += SPEED;}
掉到底下
判断字母的y坐标,如果大于屏幕高度,扣分,并且重新初始化这个字母。
if (letter[i].y >= HEIGHT){score--;letter[i].x = rand() % (WIDTH - 50) + 25;letter[i].y = rand() % HEIGHT - HEIGHT;letter[i].ch = rand() % 26 + 'A';}
MoveLetter() 函数
// 移动字母void MoveLetter(){for (int i = 0; i < MAX_LETTER; i++){letter[i].y += SPEED;if (letter[i].y >= HEIGHT){score--;letter[i].x = rand() % (WIDTH - 50) + 25;letter[i].y = rand() % HEIGHT - HEIGHT;letter[i].ch = rand() % 26 + 'A';}}}
5 绘制屏幕
字母
setbkmode函数设置字母背景的样子,这里用TRANSPARENT设为透明。
for (int i = 0; i < MAX_LETTER; i++){settextstyle(50, 20, "HandelGothic BT");setbkmode(TRANSPARENT);outtextxy(letter[i].x, letter[i].y, letter[i].ch);}
分数
sprintf_s 函数:格式化输出到一个字符数组里。
char text[20];sprintf_s(text, "Score: %d", score);settextstyle(50, 20, "Arial");outtextxy(20, 20, text);
Draw() 函数
// 绘制屏幕void Draw(){putimage(0, 0, &bk_img);for (int i = 0; i < MAX_LETTER; i++){settextstyle(50, 20, "HandelGothic BT");setbkmode(TRANSPARENT);outtextxy(letter[i].x, letter[i].y, letter[i].ch);}char text[20];sprintf_s(text, "Score: %d", score);settextstyle(50, 20, "Arial");outtextxy(20, 20, text);}
6 判断按键
// 用户输入void GetKey(){if (_kbhit()){char input = _getch();input = input - 'a' + 'A';for (int i = 0; i < MAX_LETTER; i++){if (input == letter[i].ch){score++;letter[i].x = rand() % (WIDTH - 50) + 25;letter[i].y = rand() % HEIGHT - HEIGHT;letter[i].ch = rand() % 26 + 'A';}}}}
7 音乐、背景
音乐
Playsound 函数:
BOOL PlaySound(LPCSTR pszSound, HMODULE hmod,DWORD fdwSound);
pszSound: 音乐文件路径,只能是 .wav 类型
hmod: 一般直接写 NULL ,不用管
fdwSound: 声音播放模式 ,常用:
SND_ASYNC异步播放
SND_LOOP循环播放
SND_NOSTOP不打断原来的声音
在开始时 :PlaySound(".\\Bgm.wav", NULL, SND_ASYNC | SND_LOOP);
得分时:PlaySound(".\\Get.wav", NULL, SND_ASYNC | SND_NOSTOP);
按下空格 关闭/ 打开音乐
if (input == ' '){if (isMusic){PlaySound(NULL, NULL, NULL);isMusic = false;}else{PlaySound(".\\Bgm.wav", NULL, SND_ASYNC | SND_LOOP);isMusic = true;}}
背景
主函数:loadimage(&bk_img, ".\\Background.png", WIDTH, HEIGHT, true);
Draw函数:putimage(0, 0, &bk_img);
Main函数
int main(){initgraph(WIDTH, HEIGHT);srand(time(NULL));loadimage(&bk_img, ".\\Background.png", WIDTH, HEIGHT, true);PlaySound(".\\Bgm.wav", NULL, SND_ASYNC | SND_LOOP);SetLetter();BeginBatchDraw();while (true){Draw();MoveLetter();GetKey();FlushBatchDraw();Sleep(10);}EndBatchDraw();closegraph();return 0;}
效果截图
完整代码
/** 项目名称:打字游戏* 开发环境:vs + easyx* 作者:轩* 代码长度:131 行* 完成时间:.1.1* 用时:1 小时*/#include <stdio.h>#include <graphics.h>#include <conio.h>#include <time.h>#include <mmsystem.h>#pragma comment(lib, "winmm.lib")#define WIDTH 640#define HEIGHT 480#define MAX_LETTER 10#define SPEED 2struct Letter{int x;int y;char ch;};IMAGE bk_img;Letter letter[MAX_LETTER];int score = 0; // 感谢 @ m0_74294396 提出的问题bool isMusic = true;// 初始化字母void SetLetter(){for (int i = 0; i < MAX_LETTER; i++){letter[i].x = rand() % (WIDTH - 50) + 25;letter[i].y = rand() % HEIGHT - HEIGHT;letter[i].ch = rand() % 26 + 'A';}}// 绘制屏幕void Draw(){putimage(0, 0, &bk_img);for (int i = 0; i < MAX_LETTER; i++){settextstyle(50, 20, "HandelGothic BT");setbkmode(TRANSPARENT);outtextxy(letter[i].x, letter[i].y, letter[i].ch);}char text[20];sprintf_s(text, "Score: %d", score);settextstyle(50, 20, "Arial");outtextxy(20, 20, text);}// 移动字母void MoveLetter(){for (int i = 0; i < MAX_LETTER; i++){letter[i].y += SPEED;if (letter[i].y >= HEIGHT){score--;letter[i].x = rand() % (WIDTH - 50) + 25;letter[i].y = rand() % HEIGHT - HEIGHT;letter[i].ch = rand() % 26 + 'A';}}}// 用户输入void GetKey(){if (_kbhit()){char input = _getch();if (input == ' '){if (isMusic){PlaySound(NULL, NULL, NULL);isMusic = false;}else{PlaySound(".\\Bgm.wav", NULL, SND_ASYNC | SND_LOOP);isMusic = true;}}input = input - 'a' + 'A';for (int i = 0; i < MAX_LETTER; i++){if (input == letter[i].ch){score++;PlaySound(".\\Get.wav", NULL, SND_ASYNC | SND_NOSTOP);letter[i].x = rand() % (WIDTH - 50) + 25;letter[i].y = rand() % HEIGHT - HEIGHT;letter[i].ch = rand() % 26 + 'A';}}}}int main(){initgraph(WIDTH, HEIGHT);srand(time(NULL));loadimage(&bk_img, ".\\Background.png", WIDTH, HEIGHT, true);PlaySound(".\\Bgm.wav", NULL, SND_ASYNC | SND_LOOP);SetLetter();BeginBatchDraw();while (true){Draw();MoveLetter();GetKey();FlushBatchDraw();Sleep(10);}EndBatchDraw();closegraph();return 0;}
感谢 @ m0_74294396 提出的问题,已修改!