Subversion Repositories Kolibri OS

Rev

Blame | Last modification | View Log | Download | RSS feed

  1. /******************************************************************
  2. *   21 days: a game for programmers
  3. *   Copyright (C) 2014 Maxim Grishin
  4. *
  5. *   This program is free software; you can redistribute it and/or
  6. *   modify it under the terms of the GNU General Public License
  7. *   as published by the Free Software Foundation; either version 2
  8. *   of the License, or (at your option) any later version.
  9. *
  10. *   This program is distributed in the hope that it will be useful,
  11. *   but WITHOUT ANY WARRANTY; without even the implied warranty of
  12. *   MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE.  See the
  13. *   GNU General Public License for more details.
  14. *
  15. *   You should have received a copy of the GNU General Public License
  16. *   along with this program; if not, write to the Free Software
  17. *   Foundation, Inc., 51 Franklin Street, Fifth Floor, Boston,
  18. *   MA  02110-1301, USA.
  19. *******************************************************************/
  20.  
  21. char* windowTitle = "21 days by igevorse";
  22.  
  23. #ifdef _KOS32
  24. #define kbhit kbhit // Prevent redeclaring kbhit() in pc.h
  25. #include <string>
  26. using std::string;
  27.  
  28. #pragma pack(push,1)
  29. typedef struct {
  30.     char        *name;
  31.     void        *data;
  32. } kol_struct_import;
  33. #pragma pack(pop)
  34.  
  35. void kol_exit() {
  36.     asm volatile ("int $0x40"::"a"(-1));
  37.     }
  38.  
  39. void kol_screen_get_size(unsigned *w, unsigned *h) {
  40.     unsigned size;
  41.     asm volatile ("int $0x40":"=a"(size):"a"(14));
  42.     *w = size / 65536;
  43.     *h = size % 65536;
  44.     }
  45.  
  46. void (* __attribute__((stdcall)) con_init)(unsigned w_w, unsigned w_h, unsigned s_w, unsigned s_h, const char* t);
  47. void (* __attribute__((cdecl))   printf2)(const char* format,...);
  48. void (* __attribute__((stdcall)) con_exit)(char bCloseWindow);
  49.  int (* __attribute__((stdcall)) getch)();
  50.  int (* __attribute__((stdcall)) kbhit)();
  51. void (* __attribute__((stdcall)) con_set_cursor_pos) (int x, int y);
  52.  int (* __attribute__((stdcall)) con_set_cursor_height)(int new_height);
  53. void (* __attribute__((stdcall)) cls)();
  54.  
  55. int strcmp(const char* string1, const char* string2) {
  56.         while (1) {
  57.                 if (*string1<*string2)
  58.                         return -1;
  59.                 if (*string1>*string2)
  60.                         return 1;
  61.  
  62.                 if (*string1=='\0')
  63.                         return 0;
  64.                 string1++;
  65.                 string2++;
  66.                 }
  67.         }
  68.  
  69. void* kol_cofflib_procload (kol_struct_import *imp, char *name) {
  70.         for (int i=0;;i++)
  71.                 if (NULL == ((imp+i) -> name))
  72.                         break;
  73.                 else
  74.                         if (0 == strcmp(name, (imp+i)->name) )
  75.                                 return (imp+i)->data;
  76.         return NULL;
  77.         }
  78.  
  79. kol_struct_import* kol_cofflib_load(char *name) {
  80.         kol_struct_import* val;
  81.         asm volatile ("int $0x40":"=a"(val):"a"(68), "b"(19), "c"(name));
  82.         return val;
  83.         }
  84.  
  85. unsigned _kWinWidth = 100;
  86. unsigned _kWinHeight = 30;
  87.  
  88. void getWinWH(int& width, int& height) {
  89.     width  = _kWinWidth;
  90.     height = _kWinHeight-1;
  91.     }
  92.  
  93. void CONSOLE_INIT(char* title) {
  94.     kol_struct_import *imp = kol_cofflib_load("/sys/lib/console.obj");
  95.         if (imp == 0)
  96.                 kol_exit();
  97.  
  98.         con_init = ( __attribute__((stdcall))  void (*)(unsigned, unsigned, unsigned, unsigned, const char*))
  99.                 kol_cofflib_procload (imp, "con_init");
  100.         if (con_init == NULL)
  101.                 kol_exit();
  102.  
  103.         printf2 = ( __attribute__((cdecl)) void (*)(const char*,...))
  104.                 kol_cofflib_procload (imp, "con_printf");
  105.         if (printf2 == NULL)
  106.                 kol_exit();
  107.  
  108.         con_exit = ( __attribute__((stdcall)) void (*)(char))
  109.                 kol_cofflib_procload (imp, "con_exit");
  110.         if (con_exit == NULL)
  111.                 kol_exit();
  112.  
  113.         getch = ( __attribute__((stdcall)) int (*)())
  114.                 kol_cofflib_procload (imp, "con_getch");
  115.         if (getch == NULL)
  116.                 kol_exit();
  117.  
  118.         cls = ( __attribute__((stdcall)) void (*)())
  119.                 kol_cofflib_procload (imp, "con_cls");
  120.         if (cls == NULL)
  121.                 kol_exit();
  122.  
  123.         kbhit = ( __attribute__((stdcall)) int (*)())
  124.                 kol_cofflib_procload (imp, "con_kbhit");
  125.         if (kbhit == NULL)
  126.                 kol_exit();
  127.  
  128.         con_set_cursor_pos =  ( __attribute__((stdcall)) void (*) (int, int))
  129.                 kol_cofflib_procload (imp, "con_set_cursor_pos");
  130.         if (con_set_cursor_pos == NULL)
  131.                 kol_exit();
  132.  
  133.         con_set_cursor_height = ( __attribute__((stdcall)) int (*)(int))
  134.                 kol_cofflib_procload (imp, "con_set_cursor_height");
  135.         if (con_set_cursor_height == NULL)
  136.                 kol_exit();
  137.  
  138.     unsigned sw, sh;
  139.  
  140.     kol_screen_get_size(&sw, &sh);
  141.     // Change window w/h depending on screen w/h
  142.     // Sorry for magic numbers
  143.     if (_kWinWidth*8 >= sw)
  144.         _kWinWidth = sw / 8;
  145.  
  146.     if (_kWinHeight*17 >= sh)
  147.         _kWinHeight = sh / 17;
  148.  
  149.         con_init(_kWinWidth, _kWinHeight, _kWinWidth, _kWinHeight, title);
  150.     }
  151.  
  152. void hideCursor() {
  153.         con_set_cursor_height(0);
  154.         }
  155.  
  156. void showCursor() {
  157.         //nop;
  158.         }
  159.  
  160. void consoleGoto(int line, int column) {
  161.     con_set_cursor_pos(column-1, line-1);
  162.     }
  163.  
  164. string itos(int n) {
  165.     string s;
  166.     int i, sign;
  167.  
  168.     if ((sign = n) < 0)
  169.         n = -n;
  170.     i = 0;
  171.     do {
  172.         s[i++] = n % 10 + '0';
  173.     } while ((n /= 10) > 0);
  174.     if (sign < 0)
  175.         s[i++] = '-';
  176.     s[i] = '\0';
  177.  
  178.     int j,k;
  179.     for (k = 0, j = i-1; k<j; k++, j--) {
  180.         char c = s[k];
  181.         s[k] = s[j];
  182.         s[j] = c;
  183.         }
  184.     return s;
  185.     }
  186. // Ok, I don't want to use vsprintf from KolibriOS
  187. string txt(string s, int d) {
  188.     string t = s;
  189.     unsigned i = t.find("%d");
  190.     if (i != string::npos)
  191.         t.replace(i, 2, itos(d).c_str());
  192.     return t;
  193.     }
  194.  
  195. string txt(string s, char c) {
  196.     string t = s;
  197.     unsigned i = t.find("%c");
  198.     if (i != string::npos)
  199.         t.replace(i, 2, c);
  200.     return t;
  201.     }
  202.  
  203. string txt(string s, string s2) {
  204.     string t = s;
  205.     unsigned i = t.find("%s");
  206.     if (i != string::npos)
  207.         t.replace(i, 2, s2.c_str());
  208.     return t;
  209.     }
  210.  
  211. string txt(string s, string s2, string s3) {
  212.     return txt(txt(s, s2), s3);
  213.     }
  214. string txt(string s, char ch, string s2) {
  215.     return txt(txt(s, ch), s2);
  216.     }
  217. string txt(string s, char ch, string s2, char ch2) {
  218.     return txt(txt(txt(s, ch), s2), ch2);
  219.     }
  220. string txt(string s, int d1, int d2) {
  221.     return txt(txt(s, d1), d2);
  222.     }
  223. string txt(string s, int d1, int d2, int d3) {
  224.     return txt(txt(txt(s, d1), d2), d3);
  225.     }
  226. string txt(string s, int d1, int d2, int d3, int d4) {
  227.     return txt(txt(txt(txt(s, d1), d2), d3), d4);
  228.     }
  229.  
  230. void initConsole() {
  231.     CONSOLE_INIT(windowTitle);
  232.     }
  233. #elif defined __linux__
  234. #define printf2 printf
  235. #include <cstdlib>      // system
  236. #include <stdarg.h>
  237. #include <stdio.h>  // printf, vsprintf
  238. #include <sys/ioctl.h>  // get window width/height
  239. #include <termios.h>
  240. #include <unistd.h>
  241. #include <fcntl.h>
  242. #include <string>
  243. static struct termios old, new1;
  244.  
  245. std::string txt(const char* s, ...) {
  246.     va_list args;
  247.     va_start(args,s);
  248.     char x[100000];
  249.     vsprintf(x, s, args);
  250.     va_end(args);
  251.     std::string str(x);
  252.     return str;
  253.     }
  254.  
  255. void cls() {
  256.     system("clear");
  257.     }
  258.  
  259. void hideCursor() {
  260.     printf2("\033[?25l");
  261.     }
  262.  
  263. void showCursor() {
  264.     printf2("\033[?25h");
  265.     }
  266.  
  267. void consoleGoto(int line, int column) {
  268.     printf2("\033[%d;%dH",  line, column);
  269.     }
  270.  
  271. void consoleSetColor(short text = 30, short background = 47) {
  272.     printf2("\033[%d;%dm", text, background);
  273.     }
  274.  
  275. /* Initialize new terminal i/o settings */
  276. void initTermios() {
  277.     tcgetattr(0, &old); /* grab old terminal i/o settings */
  278.     new1 = old; /* make new settings same as old settings */
  279.     new1.c_lflag &= ~ICANON; /* disable buffered i/o */
  280.     new1.c_lflag &= ~ECHO; /* set echo mode */
  281.     tcsetattr(0, TCSANOW, &new1); /* use these new terminal i/o settings now */
  282.     }
  283.  
  284. /* Restore old terminal i/o settings */
  285. void resetTermios() {
  286.     tcsetattr(0, TCSANOW, &old);
  287.     }
  288.  
  289. int kbhit () {
  290.     struct termios oldt, newt;
  291.     int ch;
  292.     int oldf;
  293.  
  294.     tcgetattr(STDIN_FILENO, &oldt);
  295.     newt = oldt;
  296.     newt.c_lflag &= ~(ICANON | ECHO);
  297.     tcsetattr(STDIN_FILENO, TCSANOW, &newt);
  298.     oldf = fcntl(STDIN_FILENO, F_GETFL, 0);
  299.     fcntl(STDIN_FILENO, F_SETFL, oldf | O_NONBLOCK);
  300.  
  301.     ch = getchar();
  302.  
  303.     tcsetattr(STDIN_FILENO, TCSANOW, &oldt);
  304.     fcntl(STDIN_FILENO, F_SETFL, oldf);
  305.  
  306.     if(ch != EOF) {
  307.         ungetc(ch, stdin);
  308.         return 1;
  309.         }
  310.     return 0;
  311.     }
  312.  
  313. /* Read 1 character without echo */
  314. char getch() {
  315.     char ch;
  316.     initTermios();
  317.     ch = getchar();
  318.     resetTermios();
  319.     return ch;
  320.     }
  321.  
  322. void getWinWH(int& width, int& height) {
  323.     struct winsize w;
  324.     ioctl(0, TIOCGWINSZ, &w);
  325.     width  = w.ws_col;
  326.     height = w.ws_row-1;
  327.     }
  328.  
  329. void initConsole() {
  330.     printf2("\033]0;%s\007", windowTitle);
  331.     }
  332. #elif defined _WIN32
  333. #define printf2 printf
  334. #include <stdio.h>  // printf, vsprintf
  335. #include <windows.h>
  336. #include <cstdlib> // system
  337. #define _NO_OLDNAMES _NO_OLDNAMES
  338. #include <conio.h> // kbhit(), getch(), getche()
  339. #include <string>
  340.  
  341. char getch() {
  342.   return _getch();
  343.   }
  344.  
  345. int kbhit (void) {
  346.   return _kbhit();
  347.   }
  348.  
  349. std::string txt(const char* s, ...) {
  350.     va_list args;
  351.     va_start(args,s);
  352.     char x[100000];
  353.     vsprintf(x, s, args);
  354.     va_end(args);
  355.     std::string str(x);
  356.     return str;
  357.     }
  358.  
  359. void cls() {
  360.     system("cls");
  361.     }
  362.  
  363. void showCursor() {
  364.     HANDLE consoleHandle = GetStdHandle(STD_OUTPUT_HANDLE);
  365.     CONSOLE_CURSOR_INFO info;
  366.     info.bVisible = TRUE;
  367.     SetConsoleCursorInfo(consoleHandle, &info);
  368.     }
  369.  
  370. void hideCursor() {
  371.     HANDLE consoleHandle = GetStdHandle(STD_OUTPUT_HANDLE);
  372.     CONSOLE_CURSOR_INFO info;
  373.     info.bVisible = FALSE;
  374.     info.dwSize = 1;
  375.     SetConsoleCursorInfo(consoleHandle, &info);
  376.     }
  377.  
  378. void consoleGoto(int line, int column) {
  379.     COORD coord;
  380.     coord.X = column;
  381.     coord.Y = line;
  382.     SetConsoleCursorPosition(GetStdHandle(STD_OUTPUT_HANDLE), coord);
  383.     }
  384.  
  385. void consoleSetColor(short text = 30, short background = 47) {
  386.     printf2("\033[%d;%dm", text, background);
  387.     }
  388.  
  389. void getWinWH(int& width, int& height) {
  390.     CONSOLE_SCREEN_BUFFER_INFO csbi;
  391.     GetConsoleScreenBufferInfo(GetStdHandle(STD_OUTPUT_HANDLE), &csbi);
  392.     width = csbi.srWindow.Right - csbi.srWindow.Left - 1;
  393.     height = csbi.srWindow.Bottom - csbi.srWindow.Top - 1;
  394.     }
  395.  
  396. void initConsole() {
  397.     SetConsoleTitle(windowTitle);
  398.     system("mode 100, 30");
  399.     }
  400. #endif
  401.