/*
world1:player can make things there
world2:player can live there to beat the boss(bushi
world3:player can make something and the others to complete it
*/
#include<cstdio>
#include<iostream>
#include<conio.h>
#include<windows.h>
#include<string>
#include<time.h>
#include<cstdlib>
#include<cmath>
#include<queue>
#define press_key(VK_NONAME) ((GetAsyncKeyState(VK_NONAME) & 0x8000) ? 1:0)
#define black 0
#define blue 1
#define green 2
#define light_green 3
#define red 4
#define purple 5
#define yellow 6
#define white 7
#define grey 8
#define little_blue 9
#define little_green 10
#define little_light_green 11
#define little_red 12
#define little_purple 13
#define little_yellow 14
#define bright_white 15
#define no 0
#define road 1
#define grass 2
#define outthing 3
#define TNT 4
#define burningthing 5
#define box 6
#define openedbox 7
#define water 8
using namespace std;
const int sl_speed=3;
const int wnum=3;
const int wlen=30;
const int wwild=30;
const int whigh=50;
string idname;
int lev=1;
int x[wnum+1],y[wnum+1],z[wnum+1],numput[wnum+1][11];
float bl[wnum+1];
char map[wnum+1][wwild+1][wlen+1][whigh+1],toput[wnum+1][11];
char boxth[wnum+1][wwild+1][wlen+1][whigh+1];
int boxnum[wnum+1][wwild+1][wlen+1][whigh+1];
struct Place{
short xx,yy,zz;
};
Place make_place(int xx,int yy,int zz){
Place res;
res.xx=(short)xx;
res.yy=(short)yy;
res.zz=(short)zz;
return res;
}
queue<Place>move[11];
/*
0:no
1:road
2:grass
3:outting
4:TNT
5:burningthing
6:box
7:openedbox
8:water
*/
void printcolor(const char* s,int color){
HANDLE handle=GetStdHandle(STD_OUTPUT_HANDLE);
SetConsoleTextAttribute(handle,/*FOREGROUND_INTENSITY|*/color);
printf(s);
SetConsoleTextAttribute(handle,/*FOREGROUND_INTENSITY|*/7);
}
/*
0 = 黑色 8 = 灰色
1 = 蓝色 9 = 淡蓝色
2 = 绿色 10 = 淡绿色
3 = 浅绿色 11 = 淡浅绿色
4 = 红色 12 = 淡红色
5 = 紫色 13 = 淡紫色
6 = 黄色 14 = 淡黄色
7 = 白色 15 = 亮白色
*/
void slprint(char *p){
while(1){
if(*p!=0)printf("%c",*p++);
else break;
Sleep(sl_speed);
}
}
void slprint(char* s,int color){
HANDLE handle=GetStdHandle(STD_OUTPUT_HANDLE);
SetConsoleTextAttribute(handle,/*FOREGROUND_INTENSITY|*/color);
slprint(s);
SetConsoleTextAttribute(handle,/*FOREGROUND_INTENSITY|*/7);
}
void gotoxy(int x,int y){
COORD pos;
pos.X=x;
pos.Y=y;
SetConsoleCursorPosition(GetStdHandle(STD_OUTPUT_HANDLE),pos);
}
int read(){
int res=0;
char ch=0;
while(ch>'9'||ch<'0')ch=getchar();
while(ch<='9'&&ch>='0'){
res=(res<<3)+(res<<1)+ch-'0';
ch=getchar();
}
return res;
}
void printname(){
cout<<idname;
printf("[lev.%d]",lev);
}
void printmap(char need_print){
switch(need_print){
case(0):printf(" ");break;
case(road):printf("■");break;
case(grass):printcolor("■",green);break;
case(outthing):printcolor("▲",red);break;
case(TNT):printcolor("■",little_red);break;
case(burningthing):printcolor("(",bright_white);printcolor(")",little_red);break;
case(box):printcolor("■",little_purple);break;
case(openedbox):printcolor("□",little_purple);break;;
case(water):printcolor("■",blue);break;
}
}
bool canin(char thing){
if(thing==water)return true;
return false;
}
bool cango(char aaa){
if(aaa==0)return false;
return true;
}
bool cangoon(char aaa){
if(aaa==0||canin(aaa))return true;
return false;
}
void born(int id){
bl[id]=10;
toput[id][1]=road;
toput[id][2]=grass;
toput[id][3]=TNT;
toput[id][4]=burningthing;
toput[id][5]=box;
toput[id][6]=water;
numput[id][1]=numput[id][2]=128;
numput[id][3]=numput[id][4]=numput[id][5]=16;
numput[id][6]=32;
while(1){
x[id]=rand()%wwild+1;
y[id]=rand()%wlen+1;
z[id]=rand()%(whigh-1)+2;
if(map[id][x[id]][y[id]][z[id]]==0&&cango(map[id][x[id]][y[id]][z[id]-1]))break;
}
}
void prework(){
srand((unsigned)time(0));
for(int i=1;i<=wnum;++i){
bl[i]=10;
for(int j=wwild/2-1;j<=wwild/2+1;++j)for(int k=wlen/2-3;k<=wlen/2+3;++k)
map[i][j][k][whigh/2]=grass;
born(i);
}
}
void add(int id,char plus_,int num){
if(plus_==0)return;
for(int i=1;i<=10;++i)if(toput[id][i]==plus_){
numput[id][i]+=num;
return;
}
for(int i=1;i<=10;++i)if(toput[id][i]==0){
toput[id][i]=plus_;
numput[id][i]=num;
return;
}
}
void add(int id,int x,int y,int z,int num){
char plus_=map[id][x][y][z];
if(plus_==box){
add(id,boxth[id][x][y][z],boxnum[id][x][y][z]);
return;
}
if(plus_==openedbox)return;
for(int i=1;i<=10;++i)if(toput[id][i]==plus_){
numput[id][i]+=num;
return;
}
for(int i=1;i<=10;++i)if(toput[id][i]==0){
toput[id][i]=plus_;
numput[id][i]=num;
return;
}
}
bool alive(int id){
if(bl[id]==0||z[id]==1)return false;
return true;
}
void print_4(int need_print){
if(need_print==0){
printf(" 0");
return;
}
int tmp_pr=need_print,cnt_pr=0;
while(tmp_pr)tmp_pr/=10,cnt_pr++;
for(int i=1;i<=4-cnt_pr;++i)putchar(' ');
if(cnt_pr>4){
tmp_pr=need_print%10000;
cnt_pr=0;
while(tmp_pr)tmp_pr/=10,cnt_pr++;
if(need_print%10000==0)cnt_pr=1;
for(int i=1;i<=4-cnt_pr;++i)putchar('0');
printf("%d",need_print%10000);
}
else printf("%d",need_print);
}
void putinbox(int id,int x,int y,int z){
printf("请选择放入的东西:\n");
Sleep(300);
int choosein=1;
while(1){
gotoxy(choosein*4-1,12);
if(press_key('F'))break;
if(_kbhit()){
int ch__=getch();
if(ch__==224)switch(getch()){
case(75):{
choosein--;
if(choosein==0)choosein=1;
break;
}
case(77):{
choosein++;
if(choosein==11)choosein=10;
break;
}
}
}
}
if(toput[id][choosein]==0||toput[id][choosein]==box||toput[id][choosein]==openedbox)
return;
system("cls");
Sleep(100);
printf("请输入放入箱子东西的数量:\n");
int num_putin=read();
if(num_putin==0)return;
if(num_putin>numput[id][choosein])num_putin=numput[id][choosein];
numput[id][choosein]-=num_putin;
boxth[id][x][y][z]=toput[id][choosein];
boxnum[id][x][y][z]=num_putin;
if(numput[id][choosein]==0)toput[id][choosein]=0;
system("cls");
}
void dfs_move(int id){
int num=move[id].size();
while(num--){
short xx=move[id].front().xx,yy=move[id].front().yy,zz=move[id].front().zz;
move[id].pop();
if(!canin(map[id][xx][yy][zz]))continue;
if(zz>1&&map[id][xx][yy][zz-1]==0){
map[id][xx][yy][zz-1]=map[id][xx][yy][zz];
map[id][xx][yy][zz]=0;
move[id].push(make_place(xx,yy,zz-1));
}
else{
if(map[id][xx][yy+1][zz]==0){
if(map[id][xx][yy+1][zz-2]!=0&&map[id][xx][yy+1][zz-1]==0){
map[id][xx][yy+1][zz-1]=map[id][xx][yy][zz];
move[id].push(make_place(xx,yy+1,zz-1));
}
else if(map[id][xx][yy+1][zz-1]!=0&&map[id][xx][yy+1][zz]==0){
map[id][xx][yy+1][zz]=map[id][xx][yy][zz];
move[id].push(make_place(xx,yy+1,zz));
}
}
if(map[id][xx][yy-1][zz]==0){
if(map[id][xx][yy-1][zz-2]!=0&&map[id][xx][yy-1][zz-1]==0){
map[id][xx][yy-1][zz-1]=map[id][xx][yy][zz];
move[id].push(make_place(xx,yy-1,zz-1));
}
else if(map[id][xx][yy-1][zz-1]!=0&&map[id][xx][yy-1][zz]==0){
map[id][xx][yy-1][zz]=map[id][xx][yy][zz];
move[id].push(make_place(xx,yy-1,zz));
}
}
if(map[id][xx+1][yy][zz]==0){
if(map[id][xx+1][yy][zz-2]!=0&&map[id][xx+1][yy][zz-1]==0){
map[id][xx+1][yy][zz-1]=map[id][xx][yy][zz];
move[id].push(make_place(xx+1,yy,zz-1));
}
else if(map[id][xx+1][yy][zz-1]!=0&&map[id][xx+1][yy][zz]==0){
map[id][xx+1][yy][zz]=map[id][xx][yy][zz];
move[id].push(make_place(xx+1,yy,zz));
}
}
if(map[id][xx-1][yy][zz]==0){
if(map[id][xx-1][yy][zz-2]!=0&&map[id][xx-1][yy][zz-1]==0){
map[id][xx-1][yy][zz-1]=map[id][xx][yy][zz];
move[id].push(make_place(xx-1,yy,zz-1));
}
else if(map[id][xx-1][yy][zz-1]!=0&&map[id][xx-1][yy][zz]==0){
map[id][xx-1][yy][zz]=map[id][xx][yy][zz];
move[id].push(make_place(xx-1,yy,zz));
}
}
}
}
}
void changeTNT(int id,int x_,int y_,int z_){
for(int i=x_-2;i<=x_+2;++i)for(int j=y_-2;j<=y_+2;++j)for(int k=z_-2;k<=z_+2;++k)
map[id][i][j][k]=0;
if(x[id]<x_-2||x[id]>x_+2||y[id]<y_-2||y[id]>y_+2||z[id]<z_-2||z[id]>z_+2)return;
int dis_TNT=abs(x[id]-x_)+abs(y[id]-y_)+abs(z[id]-z_),TNThurt;
if(dis_TNT<=2)TNThurt=8;
else if(dis_TNT<=4)TNThurt=4;
else TNThurt=2;
bl[id]=max((float)0,bl[id]-(float)TNThurt);
x[id]+=TNThurt/2*(x[id]-x_);
y[id]+=TNThurt/2*(y[id]-y_);
z[id]+=TNThurt/2*(z[id]-z_);
}
void wchange(int id,int x_,int y_,int z_){
switch(map[id][x_][y_][z_]){
case(burningthing):{
if(map[id][x_][y_][z_+1]==TNT)changeTNT(id,x_,y_,z_+1);
if(map[id][x_][y_][z_-1]==TNT)changeTNT(id,x_,y_,z_-1);
if(map[id][x_][y_+1][z_]==TNT)changeTNT(id,x_,y_+1,z_);
if(map[id][x_][y_-1][z_]==TNT)changeTNT(id,x_,y_-1,z_);
if(map[id][x_+1][y_][z_]==TNT)changeTNT(id,x_+1,y_,z_);
if(map[id][x_-1][y_][z_]==TNT)changeTNT(id,x_-1,y_,z_);
break;
}
case(water):{
move[id].push(make_place(x_,y_,z_));
break;
}
case(0):{
if(map[id][x_][y_+1][z_]==water)move[id].push(make_place(x_,y_+1,z_));
else if(map[id][x_][y_-1][z_]==water)move[id].push(make_place(x_,y_-1,z_));
else if(map[id][x_+1][y_][z_]==water)move[id].push(make_place(x_+1,y_,z_));
else if(map[id][x_-1][y_][z_]==water)move[id].push(make_place(x_-1,y_,z_));
else if(map[id][x_][y_+1][z_+1]==water)move[id].push(make_place(x_,y_+1,z_+1));
else if(map[id][x_][y_-1][z_+1]==water)move[id].push(make_place(x_,y_-1,z_+1));
else if(map[id][x_+1][y_][z_+1]==water)move[id].push(make_place(x_+1,y_,z_+1));
else if(map[id][x_-1][y_][z_+1]==water)move[id].push(make_place(x_-1,y_,z_+1));
break;
}
}
}
void wclean(int id,int x,int y,int z){
if(map[id][x][y][z]==box)map[id][x][y][z]=openedbox;
else if(map[id][x][y][z]==openedbox)map[id][x][y][z]=box,putinbox(id,x,y,z);
else map[id][x][y][z]=0;
}
void play_world(int id){
//system("color 97");
bool bui=false,chonow=false,flag=true;
int buix=x[id],buiy=y[id]+1,buiz=z[id],choput=1;
while(1){
if(flag){
gotoxy(0,0);
for(int j=y[id]-5;j<=y[id]+5;++j){
for(int i=x[id]-5;i<=x[id]+5;++i){
if(j<1||j>wlen||i<1||i>wwild)printf(" ");
else if(j==y[id]&&i==x[id])printcolor("●",bright_white);
else if(map[id][i][j][z[id]-1]!=0)printmap(map[id][i][j][z[id]-1]);
else printmap(map[id][i][j][z[id]-2]);
}
printf("\n");
}
for(int i=1;i<=bl[id];++i)printcolor("■",red);
if((int)(bl[id]*2.0)%2==1)printcolor("H ",red);
for(int i=1;i<=10.0-bl[id];++i)printcolor("□",bright_white);
printf("\n");
for(int i=1;i<=10;++i)printf(" "),printmap(toput[id][i]),printf(" ");
printf("\n");
for(int i=1;i<=10;++i)print_4(numput[id][i]);
printf("\n");
printf(" ");
gotoxy(0,14);
printf("(%d,%d,%d)\n",buix-x[id],y[id]-buiy,buiz-z[id]);
if(bui&&buiz>=z[id]-1&&buiz<=z[id]+1&&
buix>=x[id]-5&&buix<=x[id]+5&&buiy>=y[id]-5&&buiy<=y[id]+5){
gotoxy((buix-x[id]+5)<<1,buiy-y[id]+5);
printf("〇");
gotoxy(0,15);
}
flag=false;
}
if(bui){
if(press_key(' ')){
bui=false;
chonow=false;
flag=true;
Sleep(100);
}
if(press_key('F')){
flag=true;
bui=false;
if(toput[id][choput]!=0){
if(map[id][buix][buiy][buiz]==0){
numput[id][choput]--;
map[id][buix][buiy][buiz]=toput[id][choput];
wchange(id,buix,buiy,buiz);
}
else{
add(id,buix,buiy,buiz,1);
wclean(id,buix,buiy,buiz);
wchange(id,buix,buiy,buiz);
}
if(numput[id][choput]==0)toput[id][choput]=0;
}
else if(map[id][buix][buiy][buiz]!=0){
add(id,buix,buiy,buiz,1);
wclean(id,buix,buiy,buiz);
wchange(id,buix,buiy,buiz);
}
buix=x[id];
buiy=y[id]+1;
buiz=z[id];
Sleep(100);
}
if(press_key('J')){
flag=true;
bui=false;
chonow=true;
Sleep(100);
}
if(_kbhit()){
flag=true;
int ch__=getch();
if(ch__==224)switch(getch()){
case(80):buiy++;if(buiy==wlen+1)buiy=wlen;break;
case(72):buiy--;if(buiy==0)buiy=1;break;
case(75):buix--;if(buix==0)buix=1;break;
case(77):buix++;if(buix==wwild+1)buix=wwild;break;
}
}
if(press_key('T')){
flag=true;
buiz++;
if(buiz==0)buiz=1;
Sleep(100);
}
if(press_key('B')){
flag=true;
buiz--;
if(buiz==whigh+1)buiz=whigh;
Sleep(100);
}
}
else if(chonow){
if(press_key(' ')){
bui=true;
chonow=false;
flag=true;
Sleep(100);
}
gotoxy(choput*4-1,12);
if(_kbhit()){
int ch__=getch();
if(ch__==224)switch(getch()){
case(75):{
choput--;
if(choput==0)choput=1;
break;
}
case(77):{
choput++;
if(choput==11)choput=10;
break;
}
}
}
}
else{
if(press_key(' ')){
bui=true;
chonow=false;
flag=true;
Sleep(100);
}
if(press_key('J')){
flag=true;
bui=false;
chonow=true;
Sleep(100);
}
if(_kbhit()){
flag=true;
int ch__=getch();
if(ch__==224)switch(getch()){
case(80):{
if(cangoon(map[id][x[id]][y[id]+1][z[id]+1])||
cangoon(map[id][x[id]][y[id]+1][z[id]])){
if(cango(map[id][x[id]][y[id]+1][z[id]]))++z[id];
else if(cango(map[id][x[id]][y[id]+1][z[id]-1]));
else if(cango(map[id][x[id]][y[id]+1][z[id]-2]))--z[id];
y[id]++;
if(y[id]==wlen+1)y[id]=wlen;
}
break;
}
case(72):{
if(cangoon(map[id][x[id]][y[id]-1][z[id]+1])||
cangoon(map[id][x[id]][y[id]-1][z[id]])){
if(cango(map[id][x[id]][y[id]-1][z[id]]))++z[id];
else if(cango(map[id][x[id]][y[id]-1][z[id]-1]));
else if(cango(map[id][x[id]][y[id]-1][z[id]-2]))--z[id];
y[id]--;
if(y[id]==0)y[id]=1;
}
break;
}
case(75):{
if(cangoon(map[id][x[id]-1][y[id]][z[id]+1])||
cangoon(map[id][x[id]-1][y[id]][z[id]])){
if(cango(map[id][x[id]-1][y[id]][z[id]]))++z[id];
else if(cango(map[id][x[id]-1][y[id]][z[id]-1]));
else if(cango(map[id][x[id]-1][y[id]][z[id]-2]))--z[id];
x[id]--;
if(x[id]==0)x[id]=1;
}
break;
}
case(77):{
if(cangoon(map[id][x[id]+1][y[id]][z[id]+1])||
cangoon(map[id][x[id]+1][y[id]][z[id]])){
if(cango(map[id][x[id]+1][y[id]][z[id]]))++z[id];
else if(cango(map[id][x[id]+1][y[id]][z[id]-1]));
else if(cango(map[id][x[id]+1][y[id]][z[id]-2]))--z[id];
x[id]++;
if(x[id]==wwild+1)x[id]=wwild;
}
break;
}
}
}
/*if(press_key('T')){
flag=true;
z[id]--;
if(z[id]==0)break;
Sleep(100);
}
if(press_key('B')){
flag=true;
z[id]++;
if(z[id]==whigh+1)z[id]=whigh;
Sleep(100);
}*/
if(clock()%500==0)dfs_move(id),flag=true;
int cnt;
if(map[id][x[id]][y[id]][z[id]-1]==outthing&&clock()%500==0){
flag=true;
bl[id]-=0.5;
}
cnt=0;
while((map[id][x[id]][y[id]][z[id]-1]==0||
canin(map[id][x[id]][y[id]][z[id]-1])
)&&z[id]>1)
z[id]--,++cnt,flag=true;
if(z[id]!=1&&cnt>0){
if(map[id][x[id]][y[id]][z[id]-1]==outthing)bl[id]=max(0.0,bl[id]-cnt/1.0);
else if(map[id][x[id]][y[id]][z[id]]==water);
else bl[id]=max(0.0,bl[id]-cnt/2.0);
}
if(canin(map[id][x[id]][y[id]][z[id]])&&clock()%5000==0)
bl[id]=max(bl[id]-3,(float)0),flag=true;
if(bl[id]!=0&&bl[id]!=10&&clock()%2000==0)bl[id]+=0.5,flag=true;
if(!alive(id))break;
if(flag)Sleep(1);
}
}
system("cls");
printname();
if(bl[id]==0)slprint("失血过多\n");
else slprint("掉出了这个世界\n");
Sleep(2000);
born(id);
system("cls");
system("color 07");
}
void choose_world(){
slprint("Please choose the world you want.\n");
for(int i=1;i<=wnum;++i){
slprint("world ");
printf("%d\n",i);
}
int choose__=read();
system("cls");
play_world(choose__%wnum+1);
}
void look_thing(){
slprint("●",bright_white);
slprint(":你自己\n");
slprint("■");
slprint(":平地\n");
slprint("■",green);
slprint(":草地\n");
slprint(" ");
slprint(":空地\n");
slprint("▲",red);
slprint(":尖刺\n");
slprint("■",little_red);
slprint(":TNT\n");
slprint("(",bright_white);
slprint(")",little_red);
slprint(":燃料\n");
slprint("■",little_purple);
slprint(":箱子\n");
slprint("□",little_purple);
slprint(":打开的箱子\n");
slprint("■",blue);
slprint(":水\n");
system("pause");
system("cls");
}
int main(){
slprint("Welcome to the MC.\n");
slprint("[系统提示]建议全屏体验\n");
slprint("Please write down your name:\n");
cin>>idname;
slprint("Hellow,");
printname();
slprint(".\n");
system("pause");
system("cls");
slprint("[系统提示]请先将输入调制英文\n");
slprint("正在生成数据,请等待\n");
prework();
slprint("生成完成!\n");
Sleep(1000);
system("cls");
while(1){
slprint("Please choose what do you want.\n");
slprint("1 Play in the worlds.\n");
slprint("2 Look for the things in the worlds.\n");
int choose__=read();
system("cls");
if((choose__&1)==1)choose_world();
else look_thing();
}
return 0;
}