cpp
复制代码
#pragma warning(disable:4996)
#include <stdlib.h>
#include <stdio.h>
#include <easyx.h>
#include <math.h>
#include <time.h>
typedef int word;
#define SET 1
#define QUIT 2
#define KEYDOWN(vk_code) ((GetAsyncKeyState(vk_code) & 0x8000) ? 1 : 0)
struct Window {
word width;
word height;
HWND hwnd;
}win;
struct Button {
word top;
word bottom;
word left;
word right;
wchar_t* buf;
};
struct Scene {
Button* button;
}table, boot, setting;
struct Player {
double x;
double y;
word pos;
word cloth[4];
word thing[36];
word jump;
word direct;
word dy;
IMAGE img;
}player;
struct Block {
word hardness;
wchar_t name[16];
IMAGE img;
}block[256];
struct Thing {
word hardness;
wchar_t name[16];
IMAGE img;
}thing[256];
struct World {
word time;
word size;
};
struct Cache {
word id;
word block[3][256][256];
word flag[3][256][256];
}cache;
enum struct Id {
Air = 0,
Bedrock,
Soil,
Stone,
Wood,
Leaf
};
word count;
IMAGE bg;
inline void init() {
win.width = 1024;
win.height = 633;
win.hwnd = initgraph(win.width, win.height, EX_SHOWCONSOLE);
SetWindowText(win.hwnd, L"Minecraft 1.0");
BeginBatchDraw();
table.button = new Button[3];
table.button[0].top = (word)(0.375 * win.height);
table.button[0].bottom = (word)(0.5 * win.height);
table.button[0].left = (word)(0.25 * win.width);
table.button[0].right = (word)(0.75 * win.width);
table.button[0].buf = new wchar_t[16];
lstrcpyW(table.button[0].buf, L"开始");
table.button[1].top = (word)(0.5625 * win.height);
table.button[1].bottom = (word)(0.6875 * win.height);
table.button[1].left = (word)(0.25 * win.width);
table.button[1].right = (word)(0.75 * win.width);
table.button[1].buf = new wchar_t[16];
lstrcpyW(table.button[1].buf, L"设置");
table.button[2].top = (word)(0.75 * win.height);
table.button[2].bottom = (word)(0.875 * win.height);
table.button[2].left = (word)(0.25 * win.width);
table.button[2].right = (word)(0.75 * win.width);
table.button[2].buf = new wchar_t[16];
lstrcpyW(table.button[2].buf, L"退出");
loadimage(&bg, L"bg.png");
loadimage(&player.img, L"player.png");
srand(time(NULL));
{
word id = (word)Id::Bedrock;
block[id].hardness = -1;
thing[id].hardness = 0;
lstrcpyW(block[id].name, L"bedrock");
lstrcpyW(thing[id].name, L"bedblock");
loadimage(&block[id].img, L"bedrock.png");
loadimage(&thing[id++].img, L"bedblock.png");
block[id].hardness = 0;
thing[id].hardness = 0;
lstrcpyW(block[id].name, L"soil");
lstrcpyW(thing[id].name, L"soil");
loadimage(&block[id].img, L"soil.png");
loadimage(&thing[id++].img, L"soil.png");
block[id].hardness = 1;
thing[id].hardness = 0;
lstrcpyW(block[id].name, L"stone");
lstrcpyW(thing[id].name, L"stone");
loadimage(&block[id].img, L"stone.png");
loadimage(&thing[id++].img, L"stone.png");
block[id].hardness = 0;
thing[id].hardness = 0;
lstrcpyW(block[id].name, L"wood");
lstrcpyW(thing[id].name, L"wood");
loadimage(&block[id].img, L"wood.png");
loadimage(&thing[id++].img, L"wood.png");
block[id].hardness = 0;
thing[id].hardness = 0;
lstrcpyW(block[id].name, L"leaf");
lstrcpyW(thing[id].name, L"leaf");
loadimage(&block[id].img, L"leaf.png");
loadimage(&thing[id++].img, L"leaf.png");
}
}
inline bool inrectangle(word x, word y, word top, word bottom, word left, word right) {
if (x > left && x < right && y > top && y < bottom) return true;
else return false;
}
inline word welcome() {
setlinecolor(RGB(255, 255, 255));
setfillcolor(RGB(0, 0, 0));
settextcolor(RGB(255, 255, 255));
putimage(0, 0, &bg);
while (true) {
for (word i = 0; i < 3; i++) {
fillrectangle(table.button[i].left, table.button[i].top, table.button[i].right, table.button[i].bottom);
RECT r = { table.button[i].left, table.button[i].top, table.button[i].right, table.button[i].bottom };
drawtext(table.button[i].buf, &r, DT_CENTER | DT_VCENTER | DT_SINGLELINE);
FlushBatchDraw();
}
ExMessage message;
if (peekmessage(&message, EX_MOUSE) && message.lbutton) {
clearrectangle(0, 0, win.width, win.height);
FlushBatchDraw();
if (inrectangle(message.x, message.y, table.button[0].top, table.button[0].bottom, table.button[0].left, table.button[0].right)) return 0;
if (inrectangle(message.x, message.y, table.button[1].top, table.button[1].bottom, table.button[1].left, table.button[1].right)) return SET;
if (inrectangle(message.x, message.y, table.button[2].top, table.button[2].bottom, table.button[2].left, table.button[2].right)) return QUIT;
}
}
}
inline void build(word id) {
FILE* fp;
char name[16];
sprintf(name, "%d.txt", id);
fp = fopen(name, "w");
word world[256][256] = { 0 };
word flag[256][256] = { 0 };
for (word x = 0; x < 256; x++) {
world[255][x] = (word)Id::Bedrock;flag[255][x] = 1;
}
{
word type = rand() % 2;
switch (type) {
case 0: {
for (word i = 192; i < 255; i++) {
for (word j = 0; j < 256; j++) { world[i][j] = (word)Id::Stone; flag[i][j] = 1; }
}
for (word i = 188; i < 192; i++) {
for (word j = 0; j < 256; j++) { world[i][j] = (word)Id::Soil; flag[i][j] = 1; }
}
break;
}
case 1: {
for (word i = 192; i < 255; i++) {
for (word j = 0; j < 256; j++) { world[i][j] = (word)Id::Stone; flag[i][j] = 1; }
}
for (word i = 188; i < 192; i++) {
for (word j = 0; j < 256; j++) { world[i][j] = (word)Id::Soil; flag[i][j] = 1; }
}
for (word i = 4; i < 252; i += (rand() % 10 + 4)) {
world[187][i] = world[186][i] = world[185][i] = (word)Id::Wood;
world[182][i] = world[183][i - 1] = world[183][i] = world[183][i + 1] = world[184][i - 2] = world[184][i - 1] = world[184][i] = world[184][i + 1] = world[184][i + 2] = world[185][i - 1] = world[185][i + 1] = (word)Id::Leaf;
}
break;
}
}
}
for (word y = 0; y < 256; y++)for (word x = 0; x < 256; x++)fprintf(fp, "%d %d ", world[y][x], flag[y][x]); fclose(fp);
}
inline void init_block(word cid, word wid) {
FILE* fp;
char name[16];
sprintf(name, "%d.txt", wid);
fp = fopen(name, "r");
for (word i = 0; i < 256; i++) { for (word j = 0; j < 256; j++)fscanf(fp, "%d%d", &cache.block[cid][i][j], &cache.flag[cid][i][j]); }
}
inline void read() {
FILE* fp = fopen("player.txt", "r");
if (fp == NULL) { for (word i = -64; i < 64; i++) build(i); player.x = player.y = 0; cache.id = 0; }
else {
fscanf(fp, "%lf%lf", &player.x, &player.y);
for (word i = 0; i < 4; i++) fscanf(fp, "%d", &player.cloth[i]); for (word i = 0; i < 36; i++) fscanf(fp, "%d", &player.thing[i]);
cache.id = (word)floor(player.x / 256.0);
fclose(fp);
}
init_block(0, cache.id - 1); init_block(1, cache.id); init_block(2, cache.id + 1);
}
inline void movecache(word a, word b) {
for (word i = 0; i < 256; i++) {
for (word j = 0; j < 256; j++) { cache.block[a][i][j] = cache.block[b][i][j]; cache.flag[a][i][j] = cache.flag[b][i][j]; }
}
}
inline void savecache(word id, word wid) {
FILE* fp;
char name[16];
sprintf(name, "%d.txt", wid);
fp = fopen(name, "w");
for (word i = 0; i < 256; i++) { for (word j = 0; j < 256; j++)fprintf(fp, "%d %d ", cache.block[id][i][j], cache.flag[id][i][j]); }
fclose(fp);
}
inline void load() {
word px = word(player.x + 0.5);
if (px < cache.id * 256) {
savecache(2, cache.id + 1); movecache(2, 1); movecache(1, 0);
cache.id--;
FILE* fp; char name[16];
sprintf(name, "%d.txt", cache.id - 1); fp = fopen(name, "r");
if (fp == NULL) { build(cache.id - 1); fp = fopen(name, "r"); }
for (word i = 0; i < 256; i++) { for (word j = 0; j < 256; j++)fscanf(fp, "%d%d", &cache.block[0][i][j], &cache.flag[0][i][j]); }
fclose(fp);
}
if (px >= cache.id * 256 + 256) {
savecache(0, cache.id - 1); movecache(0, 1); movecache(1, 2);
cache.id++;
FILE* fp; char name[16];
sprintf(name, "%d.txt", cache.id + 1); fp = fopen(name, "r");
if (fp == NULL) { build(cache.id + 1); fp = fopen(name, "r"); }
for (word i = 0; i < 256; i++) { for (word j = 0; j < 256; j++)fscanf(fp, "%d%d", &cache.block[2][i][j], &cache.flag[2][i][j]); }
fclose(fp);
}
}
inline word input() {
if (KEYDOWN(VK_ESCAPE)) return QUIT;
if (KEYDOWN(VK_SPACE) && player.jump == 0) {
player.x = (word)(player.x + 0.5);
player.y = (word)(player.y + 0.5);
}
if (KEYDOWN('A')) { if(cache.flag[1][(word)(player.y - 0.5)][(word)(player.x + 0.4) - cache.id * 256] == 0)player.x -= 0.1; player.direct = -abs(player.direct); }
if (KEYDOWN('D')) { if(cache.flag[1][(word)(player.y - 0.5)][(word)(player.x + 0.6) - cache.id * 256] == 0)player.x += 0.1; player.direct = abs(player.direct); }
if (KEYDOWN('Z')) player.x -= 3.2;
if (KEYDOWN('C')) player.x += 3.2;
if (KEYDOWN('W') && player.jump == 0 && cache.flag[1][(word)(player.y + 1.5)][(word)(player.x + 0.5) - cache.id * 256] != 0) player.jump = -80;
if (KEYDOWN('Q') && count % 8 == 0) {
word c = 1;
word y = word(player.y + 0.5) + player.dy - 1;
word x = word(player.x + 0.5) - cache.id * 256 + player.direct;
if (x < 0) { x += 256; c--; } if (x >= 256) { x -= 256; c++; }
/*if (thing[player.thing[player.pos]].hardness >= block[cache.block[c][y][x]].hardness)*/ { cache.block[c][y][x] = (word)Id::Air; cache.flag[c][y][x] = 0; }
}
if (KEYDOWN(VK_UP) && count % 8 == 0 && player.dy > -4) player.dy--;
if (KEYDOWN(VK_DOWN) && count % 8 == 0 && player.dy < 4) player.dy++;
if (KEYDOWN(VK_LEFT) && count % 8 == 0 && abs(player.direct - 1) <= 4) player.direct--;
if (KEYDOWN(VK_RIGHT) && count % 8 == 0 && abs(player.direct + 1) <= 4) player.direct++;
if (player.jump != 0) { if (cache.flag[1][(word)(player.y + (player.jump + 40) * 0.003)][(word)(player.x + 0.5)] == 0) player.y += (player.jump + 40) * 0.003; player.jump++; }
return 0;
}
inline void output() {
word top = (word)(player.y) - 12;
word left = (word)(player.x) - 17 - cache.id * 256;
word yy = (word)(((word)player.y - player.y - 1.5) * 32);
word xx = (word)(((word)player.x - player.x - 1.5) * 32);
setlinecolor(RGB(0, 191, 255));
setfillcolor(RGB(0, 191, 255));
fillrectangle(0, 0, win.width, win.height);
putimage(496, 304, &player.img);
for (word i = 0; i < 23; i++) {
if (top + i < 0 || top + i >= 256) continue;
for (word j = 0; j < 35; j++) {
if (left + j < 0) {
if (cache.block[0][top + i][left + j + 256] != (word)Id::Air)
putimage(xx + j * 32, yy + i * 32, &block[(unsigned)cache.block[0][top + i][left + j + 256]].img);
}
else if (left + j >= 256) {
if (cache.block[2][top + i][left + j - 256] != (word)Id::Air)
putimage(xx + j * 32, yy + i * 32, &block[(unsigned)cache.block[2][top + i][left + j - 256]].img);
}
else {
if (cache.block[1][top + i][left + j] != (word)Id::Air)
putimage(xx + j * 32, yy + i * 32, &block[(unsigned)cache.block[1][top + i][left + j]].img);
}
}
}
setlinecolor(RGB(0, 0, 0));
rectangle(player.direct * 32 + 496, player.dy * 32 + 304, player.direct * 32 + 527, player.dy * 32 + 335);
FlushBatchDraw();
}
inline void craft() {
setlinecolor(RGB(127, 127, 127));
setfillcolor(RGB(127, 127, 127));
fillrectangle(0, 0, win.width, win.height);
for (word i = 0; i < 4; i++) {
;
}
for (word i = 0; i < 36; i++) {
;
}
return;
}
inline void close() {
EndBatchDraw();
closegraph();
FILE* fp = fopen("player.txt", "w");
fprintf(fp, "%lf %lf\n", player.x, player.y);
for (word i = 0; i < 4; i++) fprintf(fp, "%d ", player.cloth[i]);
fprintf(fp, "\n");
for (word i = 0; i < 36; i++) fprintf(fp, "%d ", player.thing[i]);
fprintf(fp, "\n");
fclose(fp);
savecache(0, cache.id - 1);
savecache(1, cache.id);
savecache(2, cache.id + 1);
}
int main() {
init();
{
word ret = welcome();
if (ret == SET);
if (ret == QUIT) goto CLOSE;
putimage(0, 0, &bg);
RECT r = { 0, 0, win.width, win.height };
drawtext(L"正在生成世界", &r, DT_CENTER | DT_VCENTER | DT_SINGLELINE);
FlushBatchDraw();
}
read();
player.x = (word)player.x;
player.y = (word)player.y;
while (true) {
load();
if (cache.flag[1][(word)(player.y + 0.1)][(word)(player.x + 0.5) - cache.id * 256] == 0 && player.jump == 0)
for (word tt = 0; tt < 3 && cache.flag[1][(word)(player.y + 0.1)][(word)(player.x + 0.5) - cache.id * 256] == 0; tt++) player.y += 0.1;
if (input() == QUIT)goto CLOSE;
output();
for (word t = 0; t < 2000000; t++);
count++;
}
CLOSE:
close();
return 0;
}