hxxl/project-c/main.c
2024-12-02 12:49:54 +08:00

167 lines
4.4 KiB
C

#include <windows.h>
#include <stdlib.h>
#include <time.h>
#include <stdio.h>
#define WINDOW_WIDTH 800
#define WINDOW_HEIGHT 600
#define PLAYER_WIDTH 60
#define PLAYER_HEIGHT 20
#define ENEMY_WIDTH 40
#define ENEMY_HEIGHT 20
#define BULLET_WIDTH 5
#define BULLET_HEIGHT 10
// 游戏状态
int playerX = WINDOW_WIDTH / 2; // 玩家位置
int bulletX = -1, bulletY = -1; // 子弹位置,初始不可见
int enemyX, enemyY; // 敌机位置
int score = 0; // 得分
BOOL bulletVisible = FALSE;
// 初始化敌机位置
void InitEnemy() {
enemyX = rand() % (WINDOW_WIDTH - ENEMY_WIDTH);
enemyY = 0;
}
// 碰撞检测
BOOL CheckCollision() {
return bulletX >= enemyX && bulletX <= enemyX + ENEMY_WIDTH &&
bulletY >= enemyY && bulletY <= enemyY + ENEMY_HEIGHT;
}
// 绘制游戏内容
void DrawGame(HDC hdc) {
// 清空背景
RECT rect;
rect.left = 0;
rect.top = 0;
rect.right = WINDOW_WIDTH;
rect.bottom = WINDOW_HEIGHT;
FillRect(hdc, &rect, (HBRUSH)(COLOR_WINDOW + 1));
// 绘制玩家飞船
Rectangle(hdc, playerX, WINDOW_HEIGHT - PLAYER_HEIGHT - 10,
playerX + PLAYER_WIDTH, WINDOW_HEIGHT - 10);
// 绘制子弹
if (bulletVisible) {
Rectangle(hdc, bulletX, bulletY, bulletX + BULLET_WIDTH, bulletY + BULLET_HEIGHT);
}
// 绘制敌机
Rectangle(hdc, enemyX, enemyY, enemyX + ENEMY_WIDTH, enemyY + ENEMY_HEIGHT);
// 显示分数
char scoreText[32];
sprintf(scoreText, "Score: %d", score);
TextOut(hdc, 10, 10, scoreText, strlen(scoreText));
}
// 处理窗口消息
LRESULT CALLBACK WindowProc(HWND hwnd, UINT uMsg, WPARAM wParam, LPARAM lParam) {
static HDC hdc;
static PAINTSTRUCT ps;
switch (uMsg) {
case WM_CREATE:
srand((unsigned int)time(NULL)); // 随机种子
InitEnemy();
SetTimer(hwnd, 1, 30, NULL); // 设置游戏刷新定时器
return 0;
case WM_TIMER:
// 更新子弹位置
if (bulletVisible) {
bulletY -= 10;
if (bulletY < 0) {
bulletVisible = FALSE;
}
}
// 更新敌机位置
enemyY += 5;
if (enemyY > WINDOW_HEIGHT) {
InitEnemy(); // 重新初始化敌机位置
}
// 检测碰撞
if (bulletVisible && CheckCollision()) {
score += 10;
bulletVisible = FALSE;
InitEnemy(); // 击中后重新生成敌机
}
InvalidateRect(hwnd, NULL, FALSE); // 触发重绘
return 0;
case WM_KEYDOWN:
// 控制玩家飞船移动
if (wParam == VK_LEFT && playerX > 0) {
playerX -= 10;
} else if (wParam == VK_RIGHT && playerX < WINDOW_WIDTH - PLAYER_WIDTH) {
playerX += 10;
} else if (wParam == VK_SPACE && !bulletVisible) {
// 发射子弹
bulletVisible = TRUE;
bulletX = playerX + PLAYER_WIDTH / 2;
bulletY = WINDOW_HEIGHT - PLAYER_HEIGHT - 20;
}
return 0;
case WM_PAINT:
hdc = BeginPaint(hwnd, &ps);
DrawGame(hdc);
EndPaint(hwnd, &ps);
return 0;
case WM_DESTROY:
PostQuitMessage(0);
return 0;
}
return DefWindowProc(hwnd, uMsg, wParam, lParam);
}
// WinMain 函数:程序的入口点
int WINAPI WinMain(HINSTANCE hInstance, HINSTANCE hPrevInstance, LPSTR lpCmdLine, int nCmdShow) {
const char CLASS_NAME[] = "AirplaneGame";
// 注册窗口类
WNDCLASS wc = { };
wc.lpfnWndProc = WindowProc;
wc.hInstance = hInstance;
wc.lpszClassName = CLASS_NAME;
wc.hbrBackground = (HBRUSH)(COLOR_WINDOW + 1);
RegisterClass(&wc);
// 创建窗口
HWND hwnd = CreateWindowEx(
0,
CLASS_NAME,
"打飞机游戏",
WS_OVERLAPPEDWINDOW,
CW_USEDEFAULT, CW_USEDEFAULT, WINDOW_WIDTH, WINDOW_HEIGHT,
NULL,
NULL,
hInstance,
NULL
);
if (hwnd == NULL) {
return 0;
}
ShowWindow(hwnd, nCmdShow);
// 消息循环
MSG msg = { };
while (GetMessage(&msg, NULL, 0, 0)) {
TranslateMessage(&msg);
DispatchMessage(&msg);
}
return 0;
}