Deadalus
|
00001 // Copyright (C) 2005 by Piotr Hełka (piotr.helka@nd.e-wro.pl) 00002 // Linux C++ (not full) implementation of Borland's conio.h 00003 // v 1.01 00004 // It uses Ncurses lib, so accept also its terms. 00005 00006 00007 00008 // This program is free software; you can redistribute it and/or 00009 // modify it under the terms of the GNU General Public License 00010 // as published by the Free Software Foundation; either version 2 00011 // of the License, or (at your option) any later version. 00012 // 00013 // This program is distributed in the hope that it will be useful, 00014 // but WITHOUT ANY WARRANTY; without even the implied warranty of 00015 // MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the 00016 // GNU General Public License for more details. 00017 // 00018 // You should have received a copy of the GNU General Public License 00019 // along with this program; if not, write to the Free Software 00020 // Foundation, Inc., 59 Temple Place - Suite 330, Boston, MA 02111-1307, USA. 00021 00022 // ----------------------------- krotki opis ------------------ 00023 00024 // Biblioteka obsługuje mniej lub bardziej zgodnie: 00025 // 00026 // cgets() 00027 // cputs() 00028 // clreol() 00029 // clrscr() 00030 // cprintf() 00031 // cscanf() 00032 // getch() (chyba nie wszystkie kody tak jak w conio.h) 00033 // getche() 00034 // gotoxy() 00035 // kbhit() 00036 // putch() 00037 // textbackground() 00038 // textcolor() 00039 // wherex() 00040 // wherey() 00041 // window() 00042 // 00043 // kompatbyilność w kierunku Linux CONIO.H -> DOS CONIO.H 00044 // bedzie zachowana 00045 00046 // Aby skompilowac 00047 // $g++ nazwa_progsa.cpp -lncurses -o nazwa_progsa.o 00048 00049 // ------------------------------- define --------------------- 00050 00051 #ifndef __NCURSES_H 00052 #include <ncurses.h> 00053 #endif 00054 00055 #ifndef __CONIO_H 00056 #define __CONIO_H 00057 #endif 00058 00059 #define MAX_OKIEN 256 00060 00061 #define BLACK 0 00062 #define RED 1 00063 #define GREEN 2 00064 #define BROWN 3 00065 #define BLUE 4 00066 #define MAGENTA 5 00067 #define CYAN 6 00068 #define LIGHTGRAY 7 00069 #define DARKGRAY 0 00070 #define LIGHTRED 1 00071 #define LIGHTGREEN 2 00072 #define YELLOW 3 00073 #define LIGHTBLUE 4 00074 #define PINK 5 00075 #define LIGHTCYAN 6 00076 #define WHITE 7 00077 00078 // -------------------------------- globalne ------------------ 00079 00080 //int (* wsk_f)(void) = getch; 00081 00082 #undef getch 00083 #define getch CURSgetch 00084 00085 #undef getche 00086 #define getche CURSgetche 00087 00088 00089 void inicjuj(); 00090 00091 class Startuj // konstruktor i destruktor klasy beda odpowiedzalni 00092 { public: // za automagiczna inicjalizacje ustawien ;-) 00093 Startuj(){ inicjuj(); } 00094 ~Startuj(){ endwin(); } 00095 } Start; // inicjuj! 00096 00097 typedef struct 00098 { 00099 int xup; 00100 int yup; 00101 int xdown; 00102 int ydown; 00103 WINDOW* okno; 00104 } Okno; 00105 00106 bool zainicjowane = FALSE; //czy juz po initscr() ? 00107 int znakSpecjalny = -1; //potrzebne do getch'a 00108 int n = 0; //liczba uzytych okienek 00109 00110 short kolorTekstu = COLOR_WHITE; 00111 short kolorTla = COLOR_BLACK; 00112 short biezacaPara; 00113 00114 Okno okienka[MAX_OKIEN]; //tablica struktur aktywnych okienek 00115 WINDOW* aktywneOkno = NULL; //wsk na aktywne okno 00116 00117 00118 00119 // ----------------------------- koniec globalnych ------------ 00120 00121 void inicjuj() 00122 { 00123 initscr(); 00124 start_color(); //wlaczmy kolorki 00125 cbreak(); //wylaczmy buforowanie wejscia 00126 noecho(); //bez wyswietlania na ekran 00127 //raw(); //nadpisywane i tak przez noecho 00128 keypad(stdscr, TRUE); 00129 scrollok(stdscr, TRUE); 00130 00131 //domyslne okno 00132 aktywneOkno = stdscr; 00133 zainicjowane = TRUE; 00134 00135 //utworzmy macierz 8x8 kolorow tla i tekstu 00136 short kolor = 1; 00137 for(short i=0; i<8; i++) 00138 { 00139 for(short j=0; j<8; j++, kolor++) 00140 { 00141 init_pair(kolor,i,j); 00142 if(i == COLOR_WHITE && j == COLOR_BLACK) 00143 //ustawmy czarne tlo i bialey tekst jako standard 00144 { 00145 biezacaPara = kolor; 00146 } 00147 } 00148 } 00149 00150 wrefresh(aktywneOkno); 00151 } 00152 00153 int simple_strlen(char* str) 00154 { 00155 char* p; 00156 for(p = str; *p != 0; p++); 00157 return p-str; 00158 } 00159 00160 void cputs(char* str) 00161 { 00162 waddstr(aktywneOkno, str); 00163 wrefresh(aktywneOkno); 00164 } 00165 00166 char* cgets(char* str) 00167 { // nie wiem dokladnie jak dziala orginalna f. cgets bo nie mam 00168 // do niej referencji.. 00169 if(str == NULL || *str == 0) 00170 { 00171 *(str+1) = 0; 00172 return NULL; 00173 } 00174 00175 int max = (int)(*str); 00176 00177 echo(); 00178 00179 if(wgetnstr(aktywneOkno, (str + 2), max) == ERR) 00180 { 00181 *(str+1) = 0; 00182 return NULL; 00183 } 00184 00185 noecho(); 00186 00187 *(str+1) = (char)simple_strlen(str+2); 00188 00189 return str+2; 00190 } 00191 00192 void clreol() 00193 { 00194 wclrtoeol(aktywneOkno); 00195 wrefresh(aktywneOkno); 00196 } 00197 00198 void clrscr() 00199 { 00200 if(!zainicjowane) inicjuj(); 00201 wbkgd(aktywneOkno, COLOR_PAIR(biezacaPara)); 00202 //trzeba przesunac kursor? chyba nie... 00203 wclear(aktywneOkno); 00204 } 00205 00206 int cprintf(char *fmt, ...) 00207 // czysty hardcore ;-) 00208 { 00209 if(!zainicjowane) inicjuj(); 00210 00211 va_list ap; 00212 va_start(ap, fmt); 00213 00214 int i = vwprintw(aktywneOkno,fmt, ap); //jakie proste ;-) 00215 00216 va_end(ap); 00217 00218 wrefresh(aktywneOkno); 00219 00220 return i; 00221 } 00222 00223 int cscanf(char *fmt, ...) 00224 { 00225 if(!zainicjowane) inicjuj(); 00226 00227 echo(); 00228 00229 va_list ap; 00230 va_start(ap, fmt); 00231 00232 int i = vwscanw(aktywneOkno, fmt, ap); 00233 00234 va_end(ap); 00235 00236 wrefresh(aktywneOkno); 00237 noecho(); 00238 00239 return i; 00240 } 00241 00242 int CURSgetch() 00243 { 00244 if(!zainicjowane) inicjuj(); 00245 00246 int znak; 00247 00248 if(znakSpecjalny>0) //drugi czlon znaku specjalnego 0x00 i 0x?? 00249 { 00250 //zamieniamy znak na kod DOSowy - conio.h 00251 znak = znakSpecjalny; 00252 znakSpecjalny = -1; 00253 00254 return znak-265+59; 00255 } 00256 00257 znak = wgetch(aktywneOkno); 00258 00259 if(znak > 255) //to mamy znak specjalny 0x00 00260 { 00261 znakSpecjalny = znak; 00262 return 0; 00263 } 00264 00265 return znak; 00266 } 00267 00268 int CURSgetche() 00269 { 00270 echo(); 00271 int znak = getch(); 00272 noecho(); 00273 return znak; 00274 } 00275 00276 int gotoxy(int x, int y) 00277 { 00278 if(!zainicjowane) inicjuj(); 00279 wmove(aktywneOkno, y - 1, x - 1); 00280 return 0; 00281 } 00282 00283 int kbhit() 00284 { 00285 int znak; 00286 wtimeout(aktywneOkno, 0); 00287 znak = wgetch(aktywneOkno); 00288 //wtimeout(aktywneOkno, -1); 00289 nodelay(aktywneOkno, FALSE); 00290 if (znak == ERR) return 0; 00291 ungetch(znak); 00292 return 1; 00293 } 00294 00295 int putch(int znak) 00296 { 00297 wechochar(aktywneOkno,znak); 00298 } 00299 00300 void textbackground(short kolor) 00301 { 00302 if(!zainicjowane) inicjuj(); 00303 kolorTla = kolor%8; 00304 short k=1; 00305 for(short i=0; i<8; i++) //wyszukajmy numer pary dla kolorow 00306 { 00307 for(short j=0; j<8; j++, k++) 00308 { 00309 if(kolorTekstu == i && kolorTla == j) 00310 { 00311 biezacaPara = k; 00312 wbkgd(aktywneOkno, COLOR_PAIR(k)); 00313 } 00314 } 00315 } 00316 00317 wrefresh(aktywneOkno); 00318 } 00319 00320 void textcolor(short kolor) 00321 { 00322 if(!zainicjowane) inicjuj(); 00323 kolorTekstu = kolor%8; 00324 00325 short k=1; 00326 for(short i=0; i<8; i++) //wyszukajmy numer pary dla kolorow 00327 { 00328 for(short j=0; j<8; j++, k++) 00329 { 00330 if(kolorTekstu == i && kolorTla == j) 00331 { 00332 biezacaPara = k; 00333 wcolor_set(aktywneOkno,k, NULL); 00334 } 00335 } 00336 } 00337 00338 wrefresh(aktywneOkno); 00339 } 00340 00341 int wherex(void) 00342 { 00343 if(!zainicjowane) inicjuj(); 00344 int x, y; 00345 getyx(aktywneOkno, y, x); 00346 return x + 1; 00347 } 00348 00349 int wherey(void) 00350 { 00351 if(!zainicjowane) inicjuj(); 00352 int x, y; 00353 getyx(aktywneOkno, y, x); 00354 return y + 1; 00355 } 00356 00357 void window(int xup, int yup, int xdown, int ydown) 00358 { 00359 if( xup<1 || yup<1 || xdown>COLS || ydown>LINES) 00360 { //jesli zle dane podano... 00361 xdown = COLS - xup; 00362 ydown = LINES - yup; 00363 //return; 00364 } 00365 00366 bool istnieje = FALSE; 00367 00368 if(!zainicjowane) inicjuj(); 00369 00370 /* 00371 Istnieje alternatywne rozwiazanie tworzenia nowych okien, 00372 w momencie tworzenia nowego okna, usuwa sie okno poprzednie, 00373 tzn zwalnia pamiec tego okna, komenda delwin(nzw_okna) i tworzy 00374 sie nowe okno, ustawiajac jego jako domyslne-biezace. Jednak 00375 poniewaz moze to zabierac za duzo czasu i niepotrzebnie spowolniac, 00376 majac na uwadze rozmiar dzisiejszych pamieci, postanowilem, uzyc 00377 tablicy, ktora przechowywuje wsk. na adresy okien i wykorzystuje 00378 zaalokowana juz przestrzen. Aczkolwiek mozna to w kazdej chwili zmienic. 00379 */ 00380 00381 for(int i=0; i<n && !istnieje; i++) //sprawdzimy czy podane okno juz nie 00382 // zostalo wczesniej stworzone 00383 { 00384 if( okienka[i].xup == xup && okienka[i].yup == yup 00385 && okienka[i].xdown == xdown && okienka[i].ydown == ydown) 00386 { 00387 aktywneOkno = okienka[i].okno; 00388 istnieje = TRUE; 00389 clrscr(); 00390 } 00391 } 00392 00393 if(!istnieje && n < MAX_OKIEN) //jesli nie ma takiego okna to tworzymy je 00394 { 00395 aktywneOkno = newwin(ydown - yup + 1, xdown - xup + 1, yup - 1, xup - 1); 00396 //nie dam glowy czy dokladnie tak wyswietla conio.h 00397 00398 //do tablicy zapisac... 00399 okienka[n].okno = aktywneOkno; 00400 okienka[n].xup = xup; 00401 okienka[n].yup = yup; 00402 okienka[n].xdown = xdown; 00403 okienka[n].ydown = ydown; 00404 00405 wcolor_set(aktywneOkno,biezacaPara, NULL); 00406 wbkgd(aktywneOkno, COLOR_PAIR(biezacaPara)); 00407 00408 //przywrocenie ustawien klawiszy 00409 cbreak(); //wylaczmy buforowanie wejscia 00410 noecho(); //bez wyswietlania na ekran 00411 keypad(aktywneOkno, TRUE); //pelne kody klawiszy 00412 scrollok(aktywneOkno, TRUE); 00413 00414 n++; 00415 } 00416 00417 wrefresh(aktywneOkno); 00418 00419 return; 00420 }