#include<iostream>
#include<conio.h>
#include<random>
#include <string>
#include <chrono>
#include <thread>
#include <windows.h>
using namespace std;

void color(int c)
{
    SetConsoleTextAttribute(GetStdHandle(STD_OUTPUT_HANDLE), c);
}

void selectAllConsoleText()
{

    HANDLE hConsole = GetStdHandle(STD_OUTPUT_HANDLE);

    CONSOLE_SCREEN_BUFFER_INFO csbi;
    GetConsoleScreenBufferInfo(hConsole, &csbi);

    DWORD cells = csbi.dwSize.X * csbi.dwSize.Y;
    COORD start = {0, 0};

    // Attribute: black text + white background
    WORD attribute = BACKGROUND_RED | BACKGROUND_GREEN | BACKGROUND_BLUE;

    DWORD written;

    // Change all characters' colors
    FillConsoleOutputAttribute(
        hConsole,
        attribute,
        cells,
        start,
        &written
    );

    // Keep cursor at the start
    SetConsoleCursorPosition(hConsole, start);
}

int x=55,y=207;
int fr=4;
char w[10][4][9];
char wrld[55][207];
int clr[55][207]={8};
string nick;

void out(){
    system("cls");
    color(8);
    for(int i=0;i<y+2;i++){
        cout<<"_";
    }
    for(int i=0;i<x;i++){
        cout<<"|";
        for(int j=0;j<y;j++){
            color(clr[i][j]);
            cout<<wrld[i][j];
        }
        color(8);
        cout<<"|";
        cout<<endl;
    }
    for(int i=0;i<y+2;i++){
        cout<<"-";
    }
}

void ent(){
    for(int i=0;i<88;i++){
        cout<<" ";
    }
}

int main()
{
    char h,b;
    int clra;
    char r='m';
    int qwe='-';
    cout<<"PRESS WINDOWS + UP ARROW";
    while (!((GetAsyncKeyState(VK_LWIN) & 0x8000) &&
             (GetAsyncKeyState(VK_UP) & 0x8000)))
    {

        Sleep(100);
    }
    while(r!=' '){
        system("cls");
        cout<<"---------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------"<<"\n";
        cout<<"                                                                   A NEW WORLD AWAITS THOSE WHO DARE TO ENTER. Niech gra sie zacznie!                                                                           "<<"\n";
        cout<<"---------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------"<<"\n";
        cout<<"\n"<<"\n"<<"\n"<<"\n"<<"\n"<<"\n";
        cout<<"                                                    EEEEEEE NNN    NN TTTTTTTT EEEEEEE RRRRRR       II FFFFFFF     UU    UU     DDDDDD    AAAAA  RRRRRR  EEEEEEE                                               "<<"\n";
        cout<<"                                                    EE      NNNN   NN    TT    EE      RR   RR      II FF          UU    UU     DD   DD  AA   AA RR   RR EE                                                    "<<"\n";
        cout<<"                                                    EEEEE   NN NN  NN    TT    EEEEE   RRRRRR       II FFFFF       UU    UU     DD   DD  AAAAAAA RRRRRR  EEEEE                                                 "<<"\n";
        cout<<"                                                    EE      NN  NN NN    TT    EE      RR   RR      II FF          UU    UU     DD   DD  AA   AA RR   RR EE                                                    "<<"\n";
        cout<<"                                                    EEEEEEE NN   NNNN    TT    EEEEEEE RR   RR      II FF           UUUUUU      DDDDDD   AA   AA RR   RR EEEEEEE                                               "<<"\n";
        cout<<"\n";
        cout<<"\n"<<"\n"<<"\n"<<"\n"<<"\n"<<"\n";
        cout<<"                                             .-----------------------.                                                                    .-----------------------.                                             "<<"\n";
        cout<<"                                            /  .-------------------.  \\                                                                  / ___     ___     ___   /                                              "<<"\n";
        cout<<"                                           /  /0   1      0    1   \\  \\                                                                 | [___]   [___]   [___] |                                              "<<"\n";
        cout<<"                                          |  | 1   0      1    0    |  |                                                                |                       |                                              "<<"\n";
        cout<<"                                          |  | 0   1      0         ||  |         +-----------------------------------------+           |  [=====]  [=====]     |                                              "<<"\n";
        cout<<"                                          |  | 1   0                ||  |         |          START (PRESS SPACE)            |           |  [=====]  [=====]     |                                              "<<"\n";
        cout<<"                                          |  | 0          1         ||  |         +-----------------------------------------+           |                       |                                              "<<"\n";
        cout<<"                                          |  | 1                    ||  |                                                               |  010101101011101      |                                              "<<"\n";
        cout<<"                                           \\  \\                     /  /                                                                |  110010100110100      |                                              "<<"\n";
        cout<<"                                            \\  '-------------------'  /                                                                 |                       |                                              "<<"\n";
        cout<<"                                             '-----------------------'                                                                   '-----------------------'                                             "<<"\n";    cout<<"\n"<<"\n"<<"\n";
        cout<<"\n";
        cout<<"\n";
        cout<<"\n";
        cout<<"\n";
        cout<<"\n";
        cout<<"\n";
        cout<<"\n";
        cout<<"\n";
        cout<<"\n";
        cout<<"\n";
        cout<<"\n";
        cout<<"\n";
        cout<<"\n";
        cout<<"\n";
        cout<<"\n";
        cout<<"\n";
        cout<<"\n";
        cout<<"\n";
        cout<<"\n";
        cout<<"\n";
        cout<<"\n";
        cout<<"---------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------"<<"\n";
        cout<<"\x1B[A";
        r=_getch();
    }
    system("cls");
    for(int i=1;i<=15;i++){
        color(i);
        cout<<"# ";
        if(i>9){
            cout<<" ";
        }
    }
    color(15);
    cout<<"\n";
    for(int i=1;i<=15;i++){
        cout<<i<<" ";
    }
    cout<<"\n\n";
    cout<<"Color Avatar (better type 14 or <16): ";
    cin>>clra;
    cout<<"Head: ";
    color(clra);
    h=_getch();
    cout<<h<<"\n";
    color(15);
    cout<<"Body: ";
    color(clra);
    b=_getch();
    cout<<b<<"\n";
    color(15);
    cout << "\x1B[A";   // or "\033[A"
    cout<<"\rBody:";
    color(clra);
    cout<<"<"<<b<<">\n";
    color(15);
    cout<<"Legs:";
    color(clra);
    cout<<"/ \\\n";
    cout<<"Name: ";
    cin>>nick;
    int sn=nick.size();
    this_thread::sleep_for(chrono::milliseconds(1000*2));
    system("cls");
    for(int i=0;i<23;i++){
        cout<<"\n";
    }
    ent();
    cout<<"##############################"<<"\n";
    ent();
    cout<<"#       #                    #"<<"\n";
    ent();
    cout<<"#   o   #  NAME: ";
    cout<<nick;
    for(int i=0;i<12-sn;i++){
        cout<<" ";
    }
    cout<<"#"<<"\n";
    ent();
    cout<<"#  <#>  #                    #"<<"\n";
    ent();
    cout<<"#  / \\  # PASSWORD:********  #"<<"\n";
    ent();
    cout<<"#       #                    #"<<"\n";
    ent();
    cout<<"##############################"<<"\n";

    this_thread::sleep_for(chrono::milliseconds(1000*4));

    w[0][0][0]=' ';w[0][0][1]=h;w[0][0][2]=' ';
    w[0][0][3]='-';w[0][0][4]=b;w[0][0][5]='>';
    w[0][0][6]='/';w[0][0][7]=' ';w[0][0][8]='-';

    w[0][1][0]=' ';w[0][1][1]=h;w[0][1][2]=' ';
    w[0][1][3]=' ';w[0][1][4]=b;w[0][1][5]=' ';
    w[0][1][6]=' ';w[0][1][7]='|';w[0][1][8]=' ';

    w[0][2][0]=' ';w[0][2][1]=h;w[0][2][2]=' ';
    w[0][2][3]='.';w[0][2][4]=b;w[0][2][5]=' ';
    w[0][2][6]=' ';w[0][2][7]='<';w[0][2][8]=' ';

    w[0][3][0]=' ';w[0][3][1]=h;w[0][3][2]=' ';
    w[0][3][3]='-';w[0][3][4]=b;w[0][3][5]='>';
    w[0][3][6]='<';w[0][3][7]=' ';w[0][3][8]='\\';


    w[1][0][0]=' ';w[1][0][1]=h;w[1][0][2]=' ';
    w[1][0][3]='<';w[1][0][4]=b;w[1][0][5]='-';
    w[1][0][6]='-';w[1][0][7]=' ';w[1][0][8]='\\';

    w[1][1][0]=' ';w[1][1][1]=h;w[1][1][2]=' ';
    w[1][1][3]=' ';w[1][1][4]=b;w[1][1][5]=' ';
    w[1][1][6]=' ';w[1][1][7]='|';w[1][1][8]=' ';

    w[1][2][0]=' ';w[1][2][1]=h;w[1][2][2]=' ';
    w[1][2][3]=' ';w[1][2][4]=b;w[1][2][5]='.';
    w[1][2][6]=' ';w[1][2][7]='>';w[1][2][8]=' ';

    w[1][3][0]=' ';w[1][3][1]=h;w[1][3][2]=' ';
    w[1][3][3]='<';w[1][3][4]=b;w[1][3][5]='-';
    w[1][3][6]='/';w[1][3][7]=' ';w[1][3][8]='>';


    w[2][0][0]='|';w[2][0][1]=h;w[2][0][2]=' ';
    w[2][0][3]=' ';w[2][0][4]=b;w[2][0][5]='\\';
    w[2][0][6]=' ';w[2][0][7]='[';w[2][0][8]='>';

    w[2][1][0]='|';w[2][1][1]=h;w[2][1][2]=' ';
    w[2][1][3]=' ';w[2][1][4]=b;w[2][1][5]='\\';
    w[2][1][6]=' ';w[2][1][7]='[';w[2][1][8]='>';

    w[2][2][0]=' ';w[2][2][1]=h;w[2][2][2]='|';
    w[2][2][3]='/';w[2][2][4]=b;w[2][2][5]=' ';
    w[2][2][6]='<';w[2][2][7]=']';w[2][2][8]=' ';

    w[2][3][0]=' ';w[2][3][1]=h;w[2][3][2]='|';
    w[2][3][3]='/';w[2][3][4]=b;w[2][3][5]=' ';
    w[2][3][6]='<';w[2][3][7]=']';w[2][3][8]=' ';


    w[3][0][0]=' ';w[3][0][1]=h;w[3][0][2]=' ';
    w[3][0][3]=' ';w[3][0][4]=b;w[3][0][5]='\\';
    w[3][0][6]=' ';w[3][0][7]='|';w[3][0][8]=' ';

    w[3][1][0]=' ';w[3][1][1]=h;w[3][1][2]=' ';
    w[3][1][3]=' ';w[3][1][4]=b;w[3][1][5]='\\';
    w[3][1][6]=' ';w[3][1][7]='|';w[3][1][8]=' ';

    w[3][2][0]=' ';w[3][2][1]=h;w[3][2][2]=' ';
    w[3][2][3]=' ';w[3][2][4]=b;w[3][2][5]='\\';
    w[3][2][6]=' ';w[3][2][7]='|';w[3][2][8]=' ';

    w[3][3][0]=' ';w[3][3][1]=h;w[3][3][2]=' ';
    w[3][3][3]=' ';w[3][3][4]=b;w[3][3][5]='\\';
    w[3][3][6]=' ';w[3][3][7]='|';w[3][3][8]=' ';


    w[4][0][0]=' ';w[4][0][1]=h;w[4][0][2]=' ';
    w[4][0][3]='/';w[4][0][4]=b;w[4][0][5]=' ';
    w[4][0][6]=' ';w[4][0][7]='|';w[4][0][8]=' ';

    w[4][1][0]=' ';w[4][1][1]=h;w[4][1][2]=' ';
    w[4][1][3]='/';w[4][1][4]=b;w[4][1][5]=' ';
    w[4][1][6]=' ';w[4][1][7]='|';w[4][1][8]=' ';

    w[4][2][0]=' ';w[4][2][1]=h;w[4][2][2]=' ';
    w[4][2][3]='/';w[4][2][4]=b;w[4][2][5]=' ';
    w[4][2][6]=' ';w[4][2][7]='|';w[4][2][8]=' ';

    w[4][3][0]=' ';w[4][3][1]=h;w[4][3][2]=' ';
    w[4][3][3]='/';w[4][3][4]=b;w[4][3][5]=' ';
    w[4][3][6]=' ';w[4][3][7]='|';w[4][3][8]=' ';


    w[5][0][0]=' ';w[5][0][1]=' ';w[5][0][2]=' ';
    w[5][0][3]=h;w[5][0][4]='_';w[5][0][5]=' ';
    w[5][0][6]=b;w[5][0][7]='\\';w[5][0][8]='\\';

    w[5][1][0]=' ';w[5][1][1]=' ';w[5][1][2]=' ';
    w[5][1][3]=h;w[5][1][4]='_';w[5][1][5]=' ';
    w[5][1][6]=b;w[5][1][7]='\\';w[5][1][8]='\\';

    w[5][2][0]=' ';w[5][2][1]=' ';w[5][2][2]=' ';
    w[5][2][3]=h;w[5][2][4]='_';w[5][2][5]=' ';
    w[5][2][6]=b;w[5][2][7]='\\';w[5][2][8]='\\';

    w[5][3][0]=' ';w[5][3][1]=' ';w[5][3][2]=' ';
    w[5][3][3]=h;w[5][3][4]='_';w[5][3][5]=' ';
    w[5][3][6]=b;w[5][3][7]='\\';w[5][3][8]='\\';


    w[6][0][0]='_';w[6][0][1]=h;w[6][0][2]='/';
    w[6][0][3]='`';w[6][0][4]=b;w[6][0][5]='_';
    w[6][0][6]='/';w[6][0][7]=' ';w[6][0][8]='`';

    w[6][1][0]='_';w[6][1][1]=h;w[6][1][2]='/';
    w[6][1][3]=' ';w[6][1][4]=b;w[6][1][5]='_';
    w[6][1][6]='/';w[6][1][7]=' ';w[6][1][8]=' ';

    w[6][2][0]='_';w[6][2][1]=h;w[6][2][2]='/';
    w[6][2][3]=' ';w[6][2][4]=b;w[6][2][5]='_';
    w[6][2][6]='/';w[6][2][7]=' ';w[6][2][8]=' ';

    w[6][3][0]='_';w[6][3][1]=h;w[6][3][2]='/';
    w[6][3][3]=' ';w[6][3][4]=b;w[6][3][5]='_';
    w[6][3][6]='/';w[6][3][7]=' ';w[6][3][8]=' ';

    /*for(int i=0;i<60;i++){
        system("cls");
        for(int j=0;j<i;j++){
            cout<<" ";
        }
        cout<<w[1][i%5][0]<<w[1][i%5][1]<<w[1][i%5][2]<<endl;
        for(int j=0;j<i;j++){
            cout<<" ";
        }
        cout<<w[1][i%5][3]<<w[1][i%5][4]<<w[1][i%5][5]<<endl;
        for(int j=0;j<i;j++){
            cout<<" ";
        }
        cout<<w[1][i%5][6]<<w[1][i%5][7]<<w[1][i%5][8]<<endl;
        this_thread::sleep_for(chrono::milliseconds(100));
    }
    for(int i=60;i>=0;i--){
        system("cls");
        for(int j=0;j<i;j++){
            cout<<" ";
        }
        cout<<w[0][(60-i)%5][0]<<w[0][(60-i)%5][1]<<w[0][(60-i)%5][2]<<endl;
        for(int j=0;j<i;j++){
            cout<<" ";
        }
        cout<<w[0][(60-i)%5][3]<<w[0][(60-i)%5][4]<<w[0][(60-i)%5][5]<<endl;
        for(int j=0;j<i;j++){
            cout<<" ";
        }
        cout<<w[0][(60-i)%5][6]<<w[0][(60-i)%5][7]<<w[0][(60-i)%5][8]<<endl;
        this_thread::sleep_for(chrono::milliseconds(100));
    }*/
    int posx=x-4,posy=y/2+y%2+4;
    for(int i=0;i<x;i++){
        for(int j=0;j<y;j++){
            wrld[i][j]=' ';
            clr[i][j]=8;
        }
    }
    for(int j=1;j*6<x;j++){
        for(int i=0;i<y;i++){
            wrld[j*6][i]='_';
        }
        int o=rand()%200;
        wrld[j*6][o]='!';
        clr[j*6][o]=128;
        wrld[j*6-1][o]='!';
        clr[j*6-1][o]=128;
        wrld[j*6-2][o]='!';
        clr[j*6-2][o]=128;
        wrld[j*6-3][o]='|';
        wrld[j*6-4][o]='|';
        wrld[j*6-5][o]='|';
    }
    for(int i=x-1;i>=10;i--){
        clr[i][y-10]=120;
        wrld[i][y-10]='-';
        clr[i][y-9]=120;
        wrld[i][y-9]='-';
        clr[i][y-8]=120;
        wrld[i][y-8]='-';

    }
    wrld[30][90]='I';
    clr[30][90]=2;
    wrld[29][90]='_';
    clr[29][90]=18;
    wrld[30][60]='I';
    clr[30][60]=0;
    wrld[29][60]='_';
    clr[29][60]=0;
    /*for(int i=1;i<=256;i++){
        color(i);
        cout<<"# ";
        if(i>9){
            cout<<" ";
        }
        if(i>99){
            cout<<" ";
        }
    }
    cout<<endl;
    color(15);
    for(int i=1;i<=256;i++){
        cout<<i<<" ";
    }*/
    out();
    int brd=0;
    int posoka=1;//0<- 1-> 2^v 3h<- 4h-> 5crouch 6jump
    while(1){
        int a=_getch();
        if(a=='a'&&posy-2>0&&wrld[posx][posy-1]==' '){
            posy--;
            posoka=0;
        } else if(wrld[posx][posy-2]=='H'&&a=='a'){
            posy--;
            posoka=0;
        } else if(wrld[posx][posy]=='H'&&a=='a'){
            posy--;
            posoka=0;
        } else if(wrld[posx][posy-1]=='-'&&a=='a'){
            posy--;
            posoka=0;
        }

        if(a=='d'&&posy+2<y-1&&wrld[posx][posy+1]==' '){
            posy++;
            posoka=1;
        } else if(wrld[posx][posy+2]=='H'&&a=='d'){
            posy++;
            posoka=1;
        } else if(wrld[posx][posy]=='H'&&a=='d'){
            posy++;
            posoka=1;
        } else if(wrld[posx][posy+1]=='-'&&a=='d'){
            posy++;
            posoka=1;
        }
        if(a=='D'&&posy+4<y-1&&wrld[posx][posy+1]==' '){
            posy+=3;
            posoka=1;
        }
        if(a=='A'&&posy-4>0&&wrld[posx][posy-1]==' '){
            posy-=3;
            posoka=0;
        }
        if(a=='w'&&posx>0&&wrld[posx][posy-1]=='-'&&wrld[posx][posy]=='-'&&wrld[posx][posy+1]=='-'){
            posoka=2;
            posx--;
        }
        if(a=='s'&&posx<x-2&&wrld[posx+1][posy-1]=='-'&&wrld[posx+1][posy]=='-'&&wrld[posx+1][posy+1]=='-'){
            posoka=2;
            posx++;
        }
        if(a=='e'){
            if(wrld[posx][posy-1]=='!'&&wrld[posx][posy-2]!='H'){
                wrld[posx+1][posy-2]='H';
                wrld[posx][posy-2]='H';
                wrld[posx-1][posy-2]='H';
                wrld[posx+1][posy-3]='H';
                wrld[posx][posy-3]='H';
                wrld[posx-1][posy-3]='H';
            }
            if(wrld[posx][posy+1]=='!'&&wrld[posx][posy+2]!='H'){
                wrld[posx+1][posy+2]='H';
                wrld[posx][posy+2]='H';
                wrld[posx-1][posy+2]='H';
                wrld[posx+1][posy+3]='H';
                wrld[posx][posy+3]='H';
                wrld[posx-1][posy+3]='H';
            }
            if(wrld[posx][posy-2]=='_'&&wrld[posx+1][posy-2]=='I'){
                if(wrld[posx][posy-1]=='/'){
                    wrld[posx][posy-1]=' ';
                    clr[posx][posy-1]=15;
                    cout<<"!";
                }
                posoka=4;
                wrld[posx][posy-3]='\\';
                clr[posx][posy-3]=clr[posx][posy-2];
                cout<<"11110010111100001011001001011111111110000000011010110001000001011111001001011100001010110000";
            }
            if(wrld[posx][posy+2]=='_'&&wrld[posx+1][posy+2]=='I'){
                if(wrld[posx][posy+1]=='\\'){
                    wrld[posx][posy+1]=' ';
                    clr[posx][posy+1]=15;
                }
                posoka=3;
                wrld[posx][posy+3]='/';
                clr[posx][posy+3]=clr[posx][posy+2];
                cout<<"00000010101111101001111110011110000000001001110011111111110001000001110000111010101001011100";
            }
        }
        if(a=='c'){
            posoka=5;
        }
        if(a==32){
            posoka=6;
            posx-=4;
        }
        if(a=='L'){
            selectAllConsoleText();
            this_thread::sleep_for(chrono::milliseconds(1000));
            out();
        }
        if(wrld[posx+1][posy-1]==' '&&wrld[posx+1][posy]==' '&&wrld[posx+1][posy+1]==' '){
            posx++;
        }
        brd++;
        this_thread::sleep_for(chrono::milliseconds(80));
        //(CIN
        COORD pos = {0, short(posx-1)};
        SetConsoleCursorPosition(GetStdHandle(STD_OUTPUT_HANDLE), pos);
        if(posx-1==0){
            cout<<endl;
        } else {
            color(8);
            cout<<"|";
            for(int i=0;i<y;i++){
                color(clr[posx-2][i]);
                cout<<wrld[posx-2][i];
            }
            color(8);
            cout<<"|\n";
        }
        color(15);
        cout<<"|";
        for(int i=0;i<y;i++){
            if(i==posy-1){

                for(int k=0;k<3;k++){
                    if(w[posoka][brd%fr][k]==' '){
                        color(clr[posx-1][posy+k-1]);
                        cout<<wrld[posx-1][posy+k-1];
                    }else {
                        if(wrld[posx+1][posy-1]=='-'){
                            color(clra+240);
                        } else {
                            color(clra);
                        }
                        cout<<w[posoka][brd%fr][k];
                    }
                }
                i+=2;
            } else {
                color(clr[posx-1][i]);
                cout<<wrld[posx-1][i];
            }
        }
        color(15);
        cout<<"|\n|";
        for(int i=0;i<y;i++){
             if(i==posy-1){
                for(int k=0;k<3;k++){
                    if(w[posoka][brd%fr][k+3]==' '){
                        color(clr[posx][posy+k-1]);
                        cout<<wrld[posx][posy+k-1];
                    }else {
                        if(wrld[posx+1][posy]=='-'){
                            color(clra+240);
                        } else {
                            color(clra);
                        }
                        cout<<w[posoka][brd%fr][k+3];
                    }
                }
                i+=2;
            } else {
                color(clr[posx][i]);
                cout<<wrld[posx][i];
            }

        }
        color(15);
        cout<<"|\n|";
        for(int i=0;i<y;i++){
            if(i==posy-1){
                for(int k=0;k<3;k++){
                    if(w[posoka][brd%fr][k+6]==' '){
                        color(clr[posx+1][posy+k-1]);
                        cout<<wrld[posx+1][posy+k-1];
                    }else {
                        if(wrld[posx+1][posy+1]=='-'){
                            color(clra+240);
                        } else {
                            color(clra);
                        }
                        cout<<w[posoka][brd%fr][k+6];
                    }
                }
                i+=2;
            } else {
                color(clr[posx+1][i]);
                cout<<wrld[posx+1][i];
            }
        }
        color(15);
        cout<<"|\n";
        if(posx+2<x){
            cout<<"|";
            for(int i=0;i<y;i++){
                color(clr[posx+2][i]);
                cout<<wrld[posx+2][i];
            }
            color(15);
            cout<<"|";
        }
        pos = {0, short(x+2)};
        SetConsoleCursorPosition(GetStdHandle(STD_OUTPUT_HANDLE), pos);
        cout<<"x: "<<posx<<" y: "<<posy<<"   ";
        //CIN)
    }
    return 0;
}
/*
 _/
 T
*/
