/* Tiles version of Explosion Animation */ void game::draw_explosion(int x, int y, int radius, nc_color col) { timespec ts; // Timespec for the animation of the explosion ts.tv_sec = 0; ts.tv_nsec = OPTIONS["ANIMATION_DELAY"] * EXPLOSION_MULTIPLIER; // added offset values to keep from calculating the same value over and over again. const int ypos = POSY + (y - (u.posy + u.view_offset_y)); const int xpos = POSX + (x - (u.posx + u.view_offset_x)); for (int i = 1; i <= radius; i++) { if (use_tiles) { tilecontext->init_explosion(x, y, i); } else { mvwputch(w_terrain, ypos - i, xpos - i, col, '/'); mvwputch(w_terrain, ypos - i, xpos + i, col, '\\'); mvwputch(w_terrain, ypos + i, xpos - i, col, '\\'); mvwputch(w_terrain, ypos + i, xpos + i, col, '/'); for (int j = 1 - i; j < 0 + i; j++) { mvwputch(w_terrain, ypos - i, xpos + j, col, '-'); mvwputch(w_terrain, ypos + i, xpos + j, col, '-'); mvwputch(w_terrain, ypos + j, xpos - i, col, '|'); mvwputch(w_terrain, ypos + j, xpos + i, col, '|'); } } wrefresh(w_terrain); try_update(); if( ts.tv_nsec != 0 ) { nanosleep(&ts, NULL); } } tilecontext->void_explosion(); }
/* Player hit animation */ void game::draw_hit_player(player *p, const int iDam, bool dead) { (void)dead; //unused if (use_tiles) { // get base name of player id std::string pname = (p->is_npc() ? "npc_" : "player_"); // get sex of player pname += (p->male ? "male" : "female"); tilecontext->init_draw_hit(p->posx, p->posy, pname); wrefresh(w_terrain); try_update(); timespec tspec; tspec.tv_sec = 0; tspec.tv_nsec = 1000000 * OPTIONS["ANIMATION_DELAY"]; if( tspec.tv_nsec != 0 ) { nanosleep(&tspec, NULL); } } else { hit_animation(POSX + (p->posx - (u.posx + u.view_offset_x)), POSY + (p->posy - (u.posy + u.view_offset_y)), (iDam == 0) ? yellow_background(p->symbol_color()) : red_background(p->symbol_color()), "@"); } }
// need to have a version where there is no player defined, possibly. That way shrapnel works as intended void game::draw_bullet(Creature &p, int tx, int ty, int i, std::vector<point> trajectory, char bullet_char, timespec &ts) { (void)i; //unused (void)trajectory; //unused if (u.sees(tx, ty)) { std::string bullet;// = "animation_bullet_normal"; switch(bullet_char) { case '*': bullet = "animation_bullet_normal"; break; case '#': bullet = "animation_bullet_flame"; break; case '`': bullet = "animation_bullet_shrapnel"; break; } if (use_tiles) { tilecontext->init_draw_bullet(tx, ty, bullet); } else { mvwputch(w_terrain, POSY + (ty - (u.posy + u.view_offset_y)), POSX + (tx - (u.posx + u.view_offset_x)), c_red, bullet_char); } wrefresh(w_terrain); if (p.is_player()) { try_update(); if( ts.tv_nsec != 0 ) { nanosleep(&ts, NULL); } } tilecontext->void_bullet(); } }
void putChar(char c) { if(c=='\n')//newline { y_inc(1); x_pos=0; try_update(); } else if(c=='\r')//carr return { x_pos=0; } else if(c=='\a')//alert {//no idea... } else if(c=='\b')//backspace { if(x_pos>0) { x_pos--; put_char_x_y(' ',x_pos,y_pos); } } else if(c=='\f')//form-feed { scroll_up(Y_CELLS); x_pos=0; try_update(); } else if(c=='\t')//hrz tab { x_inc(HTABS); } else if(c=='\v')//vert tab { y_inc(VTABS); try_update(); } else { put_char_x_y(c,x_pos,y_pos); x_inc(1); } }
static void x_inc(int n) { x_pos+=n; if(x_pos>=X_CELLS) { int newx=x_pos%X_CELLS; y_inc(x_pos/X_CELLS); x_pos=newx; try_update(); } }
void game::draw_hit_mon( const tripoint &p, const monster &m, bool const dead ) { if (!use_tiles) { draw_hit_mon_curses( p, m, u, dead ); return; } tilecontext->init_draw_hit( p, m.type->id ); wrefresh(w_terrain); try_update(); draw_animation_delay(); }
void game::draw_explosion( const tripoint &p, int const r, nc_color const col ) { if (!use_tiles) { draw_explosion_curses(*this, p, r, col); return; } for (int i = 1; i <= r; i++) { tilecontext->init_explosion( p, i ); // TODO not xpos ypos? wrefresh(w_terrain); try_update(); draw_animation_delay(EXPLOSION_MULTIPLIER); } if (r > 0) { tilecontext->void_explosion(); } }
void game::draw_hit_player(player const &p, const int dam) { if (!use_tiles) { draw_hit_player_curses(*this, p, dam); return; } static std::string const player_male {"player_male"}; static std::string const player_female {"player_female"}; static std::string const npc_male {"npc_male"}; static std::string const npc_female {"npc_female"}; std::string const& type = p.is_player() ? (p.male ? player_male : player_female) : (p.male ? npc_male : npc_female); tilecontext->init_draw_hit( p.pos3(), type ); wrefresh(w_terrain); try_update(); draw_animation_delay(); }
/* Monster hit animation */ void game::draw_hit_mon(int x, int y, monster m, bool dead) { if (use_tiles) { //int iTimeout = 0; tilecontext->init_draw_hit(x, y, m.type->id); wrefresh(w_terrain); try_update(); timespec tspec; tspec.tv_sec = 0; tspec.tv_nsec = BULLET_SPEED; nanosleep(&tspec, NULL); } else { nc_color cMonColor = m.type->color; char sMonSym = m.symbol(); hit_animation(POSX + (x - (u.posx + u.view_offset_x)), POSY + (y - (u.posy + u.view_offset_y)), red_background(cMonColor), dead ? '%' : sMonSym); } }
// need to have a version where there is no player defined, possibly. That way shrapnel works as intended void game::draw_bullet(Creature const &p, const tripoint &t, int const i, std::vector<tripoint> const &trajectory, char const bullet) { //TODO signature and impl could be changed to eliminate these params (void)i; //unused (void)trajectory; //unused if( !u.sees( t ) ) { return; } if (!use_tiles) { draw_bullet_curses(w_terrain, u, m, t, bullet, nullptr, p.is_player()); return; } static std::string const bullet_unknown {}; static std::string const bullet_normal {"animation_bullet_normal"}; static std::string const bullet_flame {"animation_bullet_flame"}; static std::string const bullet_shrapnel {"animation_bullet_shrapnel"}; std::string const &bullet_type = (bullet == '*') ? bullet_normal : (bullet == '#') ? bullet_flame : (bullet == '`') ? bullet_shrapnel : bullet_unknown; tilecontext->init_draw_bullet( t, bullet_type ); wrefresh(w_terrain); if( p.is_player() ) { try_update(); draw_animation_delay(); } tilecontext->void_bullet(); }
/* Monster hit animation */ void game::draw_hit_mon(int x, int y, monster m, bool dead) { if (use_tiles) { //int iTimeout = 0; tilecontext->init_draw_hit(x, y, m.type->id); wrefresh(w_terrain); try_update(); timespec tspec; tspec.tv_sec = 0; tspec.tv_nsec = 1000000 * OPTIONS["ANIMATION_DELAY"]; if( tspec.tv_nsec != 0 ) { nanosleep(&tspec, NULL); } } else { nc_color cMonColor = m.type->color; const std::string &sMonSym = m.symbol(); hit_animation(POSX + (x - (u.posx + u.view_offset_x)), POSY + (y - (u.posy + u.view_offset_y)), red_background(cMonColor), dead ? "%" : sMonSym); } }
//Check for any window messages (keypress, paint, mousemove, etc) void CheckMessages() { SDL_Event ev; bool quit = false; while(SDL_PollEvent(&ev)) { switch(ev.type) { case SDL_KEYDOWN: { int lc = 0; if(OPTIONS[OPT_HIDE_CURSOR] > 0 && SDL_ShowCursor(-1)) SDL_ShowCursor(SDL_DISABLE); //hide mouse cursor on keyboard input Uint8 *keystate = SDL_GetKeyState(NULL); // manually handle Alt+F4 for older SDL lib, no big deal if(ev.key.keysym.sym==SDLK_F4 && (keystate[SDLK_RALT] || keystate[SDLK_LALT]) ) { quit = true; break; } else if(ev.key.keysym.sym==SDLK_RSHIFT || ev.key.keysym.sym==SDLK_LSHIFT || ev.key.keysym.sym==SDLK_RCTRL || ev.key.keysym.sym==SDLK_LCTRL ) { break; // temporary fix for unwanted keys } else if(ev.key.keysym.sym==SDLK_RALT || ev.key.keysym.sym==SDLK_LALT) { begin_alt_code(); break; } else if (ev.key.keysym.unicode != 0) { lc = ev.key.keysym.unicode; switch (lc){ case 13: //Reroute ENTER key for compatilbity purposes lc=10; break; case 8: //Reroute BACKSPACE key for compatilbity purposes lc=127; break; } } if(ev.key.keysym.sym==SDLK_LEFT) { lc = KEY_LEFT; } else if(ev.key.keysym.sym==SDLK_RIGHT) { lc = KEY_RIGHT; } else if(ev.key.keysym.sym==SDLK_UP) { lc = KEY_UP; } else if(ev.key.keysym.sym==SDLK_DOWN) { lc = KEY_DOWN; } else if(ev.key.keysym.sym==SDLK_PAGEUP) { lc = KEY_PPAGE; } else if(ev.key.keysym.sym==SDLK_PAGEDOWN) { lc = KEY_NPAGE; } if(!lc) break; if(alt_down) { add_alt_code(lc); }else { lastchar = lc; } } break; case SDL_KEYUP: { if(ev.key.keysym.sym==SDLK_RALT || ev.key.keysym.sym==SDLK_LALT) { int code = end_alt_code(); if(code) lastchar = code; } } break; case SDL_MOUSEMOTION: if((OPTIONS[OPT_HIDE_CURSOR] == 0 || OPTIONS[OPT_HIDE_CURSOR] == 2) && !SDL_ShowCursor(-1)) SDL_ShowCursor(SDL_ENABLE); break; case SDL_QUIT: quit = true; break; } } if (needupdate) try_update(); if(quit) { endwin(); exit(0); } }
void curses_drawwindow(WINDOW *win) { int i,j,w,drawx,drawy; unsigned tmp; for (j=0; j<win->height; j++){ if (win->line[j].touched) { needupdate = true; win->line[j].touched=false; for (i=0,w=0; w<win->width; i++,w++){ drawx=((win->x+w)*fontwidth); drawy=((win->y+j)*fontheight);//-j; if (((drawx+fontwidth)<=WindowWidth) && ((drawy+fontheight)<=WindowHeight)){ const char* utf8str = win->line[j].chars+i; int len = ANY_LENGTH; tmp = UTF8_getch(&utf8str, &len); int FG = win->line[j].FG[w]; int BG = win->line[j].BG[w]; FillRectDIB(drawx,drawy,fontwidth,fontheight,BG); if ( tmp != UNKNOWN_UNICODE){ int cw = mk_wcwidth((wchar_t)tmp); len = ANY_LENGTH-len; if(cw>1) { FillRectDIB(drawx+fontwidth*(cw-1),drawy,fontwidth,fontheight,BG); w+=cw-1; } if(len>1) { i+=len-1; } if(tmp) OutputChar(tmp, drawx,drawy,FG); } else { switch ((unsigned char)win->line[j].chars[i]) { case LINE_OXOX_C://box bottom/top side (horizontal line) HorzLineDIB(drawx,drawy+halfheight,drawx+fontwidth,1,FG); break; case LINE_XOXO_C://box left/right side (vertical line) VertLineDIB(drawx+halfwidth,drawy,drawy+fontheight,2,FG); break; case LINE_OXXO_C://box top left HorzLineDIB(drawx+halfwidth,drawy+halfheight,drawx+fontwidth,1,FG); VertLineDIB(drawx+halfwidth,drawy+halfheight,drawy+fontheight,2,FG); break; case LINE_OOXX_C://box top right HorzLineDIB(drawx,drawy+halfheight,drawx+halfwidth,1,FG); VertLineDIB(drawx+halfwidth,drawy+halfheight,drawy+fontheight,2,FG); break; case LINE_XOOX_C://box bottom right HorzLineDIB(drawx,drawy+halfheight,drawx+halfwidth,1,FG); VertLineDIB(drawx+halfwidth,drawy,drawy+halfheight+1,2,FG); break; case LINE_XXOO_C://box bottom left HorzLineDIB(drawx+halfwidth,drawy+halfheight,drawx+fontwidth,1,FG); VertLineDIB(drawx+halfwidth,drawy,drawy+halfheight+1,2,FG); break; case LINE_XXOX_C://box bottom north T (left, right, up) HorzLineDIB(drawx,drawy+halfheight,drawx+fontwidth,1,FG); VertLineDIB(drawx+halfwidth,drawy,drawy+halfheight,2,FG); break; case LINE_XXXO_C://box bottom east T (up, right, down) VertLineDIB(drawx+halfwidth,drawy,drawy+fontheight,2,FG); HorzLineDIB(drawx+halfwidth,drawy+halfheight,drawx+fontwidth,1,FG); break; case LINE_OXXX_C://box bottom south T (left, right, down) HorzLineDIB(drawx,drawy+halfheight,drawx+fontwidth,1,FG); VertLineDIB(drawx+halfwidth,drawy+halfheight,drawy+fontheight,2,FG); break; case LINE_XXXX_C://box X (left down up right) HorzLineDIB(drawx,drawy+halfheight,drawx+fontwidth,1,FG); VertLineDIB(drawx+halfwidth,drawy,drawy+fontheight,2,FG); break; case LINE_XOXX_C://box bottom east T (left, down, up) VertLineDIB(drawx+halfwidth,drawy,drawy+fontheight,2,FG); HorzLineDIB(drawx,drawy+halfheight,drawx+halfwidth,1,FG); break; default: break; } };//switch (tmp) }//(tmp < 0) };//for (i=0;i<_windows[w].width;i++) } };// for (j=0;j<_windows[w].height;j++) win->draw=false; //We drew the window, mark it as so if (needupdate) try_update(); }
//Check for any window messages (keypress, paint, mousemove, etc) void CheckMessages() { SDL_Event ev; bool quit = false; if(HandleDPad()) { return; } lastchar_is_mouse = false; while(SDL_PollEvent(&ev)) { switch(ev.type) { case SDL_KEYDOWN: { int lc = 0; //hide mouse cursor on keyboard input if(OPTIONS["HIDE_CURSOR"] != "show" && SDL_ShowCursor(-1)) { SDL_ShowCursor(SDL_DISABLE); } Uint8 *keystate = SDL_GetKeyState(NULL); // manually handle Alt+F4 for older SDL lib, no big deal if( ev.key.keysym.sym == SDLK_F4 && (keystate[SDLK_RALT] || keystate[SDLK_LALT]) ) { quit = true; break; } else if( ev.key.keysym.sym == SDLK_RSHIFT || ev.key.keysym.sym == SDLK_LSHIFT || ev.key.keysym.sym == SDLK_RCTRL || ev.key.keysym.sym == SDLK_LCTRL || ev.key.keysym.sym == SDLK_RALT ) { break; // temporary fix for unwanted keys } else if( ev.key.keysym.sym == SDLK_LALT ) { begin_alt_code(); break; } else if( ev.key.keysym.unicode != 0 ) { lc = ev.key.keysym.unicode; switch (lc){ case 13: //Reroute ENTER key for compatilbity purposes lc=10; break; case 8: //Reroute BACKSPACE key for compatilbity purposes lc=127; break; } } if( ev.key.keysym.sym == SDLK_LEFT ) { lc = KEY_LEFT; } else if( ev.key.keysym.sym == SDLK_RIGHT ) { lc = KEY_RIGHT; } else if( ev.key.keysym.sym == SDLK_UP ) { lc = KEY_UP; } else if( ev.key.keysym.sym == SDLK_DOWN ) { lc = KEY_DOWN; } else if( ev.key.keysym.sym == SDLK_PAGEUP ) { lc = KEY_PPAGE; } else if( ev.key.keysym.sym == SDLK_PAGEDOWN ) { lc = KEY_NPAGE; } if( !lc ) { break; } if( alt_down ) { add_alt_code( lc ); } else { lastchar = lc; } lastchar_isbutton = false; } break; case SDL_KEYUP: { if( ev.key.keysym.sym == SDLK_LALT ) { int code = end_alt_code(); if( code ) { lastchar = code; } } } break; case SDL_JOYBUTTONDOWN: lastchar = ev.jbutton.button; lastchar_isbutton = true; break; case SDL_JOYAXISMOTION: // on gamepads, the axes are the analog sticks // TODO: somehow get the "digipad" values from the axes break; case SDL_MOUSEMOTION: if( (OPTIONS["HIDE_CURSOR"] == "show" || OPTIONS["HIDE_CURSOR"] == "hidekb") && !SDL_ShowCursor(-1)) { SDL_ShowCursor(SDL_ENABLE); } break; case SDL_MOUSEBUTTONUP: if (ev.button.button == SDL_BUTTON_LEFT) { lastchar_is_mouse = true; lastchar = MOUSE_BUTTON_LEFT; } else if (ev.button.button == SDL_BUTTON_RIGHT) { lastchar_is_mouse = true; lastchar = MOUSE_BUTTON_RIGHT; } else if (ev.button.button == SDL_BUTTON_WHEELUP) { // Mouse wheel emulates '<' and '>' // FIXME This should really find current key from 'keymap', in case it's remapped, but // that's in action.h. When that's available at a different abstraction level, // this can be improved. lastchar = '<'; } else if (ev.button.button == SDL_BUTTON_WHEELDOWN) { lastchar = '>'; } break; case SDL_QUIT: quit = true; break; } } #ifdef SDLTILES if (needupdate) { try_update(); } #endif if(quit) { endwin(); exit(0); } }
//Check for any window messages (keypress, paint, mousemove, etc) void CheckMessages() { SDL_Event ev; bool quit = false; if(HandleDPad()) { return; } lastchar_is_mouse = false; while(SDL_PollEvent(&ev)) { switch(ev.type) { case SDL_KEYDOWN: { int lc = 0; //hide mouse cursor on keyboard input if(OPTIONS["HIDE_CURSOR"] != "show" && SDL_ShowCursor(-1)) { SDL_ShowCursor(SDL_DISABLE); } Uint8 *keystate = SDL_GetKeyState(NULL); // manually handle Alt+F4 for older SDL lib, no big deal if( ev.key.keysym.sym == SDLK_F4 && (keystate[SDLK_RALT] || keystate[SDLK_LALT]) ) { quit = true; break; } if( ev.key.keysym.unicode != 0 ) { lc = ev.key.keysym.unicode; switch (lc){ case 13: //Reroute ENTER key for compatilbity purposes lc=10; break; case 8: //Reroute BACKSPACE key for compatilbity purposes lc=127; break; } } switch (ev.key.keysym.sym) { case SDLK_RSHIFT||SDLK_LSHIFT||SDLK_RCTRL||SDLK_LCTRL||SDLK_RALT: lc= 0; break; // temporary fix for unwanted keys case SDLK_LALT: begin_alt_code(); break; case SDLK_LEFT: lc = KEY_LEFT; break; case SDLK_RIGHT: lc = KEY_RIGHT; break; case SDLK_UP: lc = KEY_UP; break; case SDLK_DOWN: lc = KEY_DOWN; break; case SDLK_PAGEUP: lc = KEY_PPAGE; break; case SDLK_PAGEDOWN: lc = KEY_NPAGE; break; } if( !lc ) { break; } if( alt_down ) { add_alt_code( lc ); } else { lastchar = lc; } lastchar_isbutton = false; } break; case SDL_KEYUP: { if( ev.key.keysym.sym == SDLK_LALT ) { int code = end_alt_code(); if( code ) { lastchar = code; } } } break; case SDL_JOYBUTTONDOWN: lastchar = ev.jbutton.button; lastchar_isbutton = true; break; case SDL_JOYAXISMOTION: // on gamepads, the axes are the analog sticks // TODO: somehow get the "digipad" values from the axes break; case SDL_MOUSEMOTION: if (OPTIONS["HIDE_CURSOR"] == "show" || OPTIONS["HIDE_CURSOR"] == "hidekb") { if (!SDL_ShowCursor(-1)) { SDL_ShowCursor(SDL_ENABLE); } // Only monitor motion when cursor is visible lastchar_is_mouse = true; lastchar = MOUSE_MOVE; } break; case SDL_MOUSEBUTTONUP: lastchar_is_mouse = true; switch (ev.button.button) { case SDL_BUTTON_LEFT: lastchar = MOUSE_BUTTON_LEFT; break; case SDL_BUTTON_RIGHT: lastchar = MOUSE_BUTTON_RIGHT; break; case SDL_BUTTON_WHEELUP: lastchar = SCROLLWHEEL_UP; break; case SDL_BUTTON_WHEELDOWN: lastchar = SCROLLWHEEL_DOWN; break; } break; case SDL_QUIT: quit = true; break; } } #ifdef SDLTILES if (needupdate) { try_update(); } #endif if(quit) { endwin(); exit(0); } }
void curses_drawwindow(WINDOW *win) { int i,j,w,drawx,drawy; unsigned tmp; SDL_Rect update_rect; update_rect.x = win->x * fontwidth; update_rect.w = win->width * fontwidth; update_rect.y = 9999; // default value update_rect.h = 9999; // default value int jr = 0; for (j=0; j<win->height; j++){ if (win->line[j].touched) { if (update_rect.y == 9999) { update_rect.y = (win->y+j)*fontheight; jr=j; } update_rect.h = (j-jr+1)*fontheight; needupdate = true; win->line[j].touched=false; for (i=0,w=0; w<win->width; i++,w++){ drawx=((win->x+w)*fontwidth); drawy=((win->y+j)*fontheight);//-j; if (((drawx+fontwidth)<=WindowWidth) && ((drawy+fontheight)<=WindowHeight)){ const char* utf8str = win->line[j].chars+i; int len = ANY_LENGTH; tmp = UTF8_getch(&utf8str, &len); int FG = win->line[j].FG[w]; int BG = win->line[j].BG[w]; FillRectDIB(drawx,drawy,fontwidth,fontheight,BG); if ( tmp != UNKNOWN_UNICODE){ int cw = mk_wcwidth(tmp); len = ANY_LENGTH-len; if(cw>1) { FillRectDIB(drawx+fontwidth*(cw-1),drawy,fontwidth,fontheight,BG); w+=cw-1; } if(len>1) { i+=len-1; } if(tmp) OutputChar(tmp, drawx,drawy,FG); } else { switch ((unsigned char)win->line[j].chars[i]) { case LINE_OXOX_C://box bottom/top side (horizontal line) HorzLineDIB(drawx,drawy+halfheight,drawx+fontwidth,1,FG); break; case LINE_XOXO_C://box left/right side (vertical line) VertLineDIB(drawx+halfwidth,drawy,drawy+fontheight,2,FG); break; case LINE_OXXO_C://box top left HorzLineDIB(drawx+halfwidth,drawy+halfheight,drawx+fontwidth,1,FG); VertLineDIB(drawx+halfwidth,drawy+halfheight,drawy+fontheight,2,FG); break; case LINE_OOXX_C://box top right HorzLineDIB(drawx,drawy+halfheight,drawx+halfwidth,1,FG); VertLineDIB(drawx+halfwidth,drawy+halfheight,drawy+fontheight,2,FG); break; case LINE_XOOX_C://box bottom right HorzLineDIB(drawx,drawy+halfheight,drawx+halfwidth,1,FG); VertLineDIB(drawx+halfwidth,drawy,drawy+halfheight+1,2,FG); break; case LINE_XXOO_C://box bottom left HorzLineDIB(drawx+halfwidth,drawy+halfheight,drawx+fontwidth,1,FG); VertLineDIB(drawx+halfwidth,drawy,drawy+halfheight+1,2,FG); break; case LINE_XXOX_C://box bottom north T (left, right, up) HorzLineDIB(drawx,drawy+halfheight,drawx+fontwidth,1,FG); VertLineDIB(drawx+halfwidth,drawy,drawy+halfheight,2,FG); break; case LINE_XXXO_C://box bottom east T (up, right, down) VertLineDIB(drawx+halfwidth,drawy,drawy+fontheight,2,FG); HorzLineDIB(drawx+halfwidth,drawy+halfheight,drawx+fontwidth,1,FG); break; case LINE_OXXX_C://box bottom south T (left, right, down) HorzLineDIB(drawx,drawy+halfheight,drawx+fontwidth,1,FG); VertLineDIB(drawx+halfwidth,drawy+halfheight,drawy+fontheight,2,FG); break; case LINE_XXXX_C://box X (left down up right) HorzLineDIB(drawx,drawy+halfheight,drawx+fontwidth,1,FG); VertLineDIB(drawx+halfwidth,drawy,drawy+fontheight,2,FG); break; case LINE_XOXX_C://box bottom east T (left, down, up) VertLineDIB(drawx+halfwidth,drawy,drawy+fontheight,2,FG); HorzLineDIB(drawx,drawy+halfheight,drawx+halfwidth,1,FG); break; default: break; } };//switch (tmp) }//(tmp < 0) };//for (i=0;i<_windows[w].width;i++) } };// for (j=0;j<_windows[w].height;j++) win->draw=false; //We drew the window, mark it as so if (g && win == g->w_terrain && use_tiles) { update_rect.y = win->y*tilecontext->tile_height; update_rect.h = win->height*tilecontext->tile_height; update_rect.x = win->y*tilecontext->tile_width; update_rect.w = win->width*tilecontext->tile_width; //GfxDraw(thegame, win->x*fontwidth, win->y*fontheight, thegame->terrain_view_x, thegame->terrain_view_y, win->width*fontwidth, win->height*fontheight); tilecontext->draw(win->x * fontwidth, win->y * fontheight, g->ter_view_x, g->ter_view_y, tilecontext->terrain_term_x * fontwidth, tilecontext->terrain_term_y * fontheight); } //*/ if (update_rect.y != 9999) { SDL_UpdateRect(screen, update_rect.x, update_rect.y, update_rect.w, update_rect.h); } if (needupdate) try_update(); }
//Check for any window messages (keypress, paint, mousemove, etc) void CheckMessages() { SDL_Event ev; bool quit = false; if(HandleDPad()) { return; } lastchar_is_mouse = false; while(SDL_PollEvent(&ev)) { switch(ev.type) { case SDL_WINDOWEVENT: switch(ev.window.event) { case SDL_WINDOWEVENT_SHOWN: case SDL_WINDOWEVENT_EXPOSED: case SDL_WINDOWEVENT_RESTORED: needupdate = true; break; default: break; } break; case SDL_KEYDOWN: { int lc = 0; //hide mouse cursor on keyboard input if(OPTIONS["HIDE_CURSOR"] != "show" && SDL_ShowCursor(-1)) { SDL_ShowCursor(SDL_DISABLE); } const Uint8 *keystate = SDL_GetKeyboardState(NULL); // manually handle Alt+F4 for older SDL lib, no big deal if( ev.key.keysym.sym == SDLK_F4 && (keystate[SDL_SCANCODE_RALT] || keystate[SDL_SCANCODE_LALT]) ) { quit = true; break; } switch (ev.key.keysym.sym) { case SDLK_KP_ENTER: case SDLK_RETURN: case SDLK_RETURN2: lc = 10; break; case SDLK_BACKSPACE: case SDLK_KP_BACKSPACE: lc = 127; break; case SDLK_ESCAPE: lc = 27; break; case SDLK_TAB: lc = 9; break; case SDLK_RALT: case SDLK_LALT: begin_alt_code(); break; case SDLK_LEFT: lc = KEY_LEFT; break; case SDLK_RIGHT: lc = KEY_RIGHT; break; case SDLK_UP: lc = KEY_UP; break; case SDLK_DOWN: lc = KEY_DOWN; break; case SDLK_PAGEUP: lc = KEY_PPAGE; break; case SDLK_PAGEDOWN: lc = KEY_NPAGE; break; } if( !lc ) { break; } if( alt_down ) { add_alt_code( lc ); } else { lastchar = lc; } lastchar_isbutton = false; } break; case SDL_KEYUP: { if( ev.key.keysym.sym == SDLK_LALT || ev.key.keysym.sym == SDLK_RALT ) { int code = end_alt_code(); if( code ) { lastchar = code; } } } break; case SDL_TEXTINPUT: lastchar = *ev.text.text; break; case SDL_JOYBUTTONDOWN: lastchar = ev.jbutton.button; lastchar_isbutton = true; break; case SDL_JOYAXISMOTION: // on gamepads, the axes are the analog sticks // TODO: somehow get the "digipad" values from the axes break; case SDL_MOUSEMOTION: if (OPTIONS["HIDE_CURSOR"] == "show" || OPTIONS["HIDE_CURSOR"] == "hidekb") { if (!SDL_ShowCursor(-1)) { SDL_ShowCursor(SDL_ENABLE); } // Only monitor motion when cursor is visible lastchar_is_mouse = true; lastchar = MOUSE_MOVE; } break; case SDL_MOUSEBUTTONUP: lastchar_is_mouse = true; switch (ev.button.button) { case SDL_BUTTON_LEFT: lastchar = MOUSE_BUTTON_LEFT; break; case SDL_BUTTON_RIGHT: lastchar = MOUSE_BUTTON_RIGHT; break; } break; case SDL_MOUSEWHEEL: lastchar_is_mouse = true; if(ev.wheel.y > 0) { lastchar = SCROLLWHEEL_UP; } else if(ev.wheel.y < 0) { lastchar = SCROLLWHEEL_DOWN; } break; case SDL_QUIT: quit = true; break; } } #ifdef SDLTILES if (needupdate) { try_update(); } #endif if(quit) { endwin(); exit(0); } }
static void put_char_x_y(char c, int x, int y) { char *p=get_c_ptr(x,y); *p=c; try_update();//first character only looks ugly.. do on newline instead.. also on wraps }
void game::draw_custom_explosion( const tripoint &, const std::map<tripoint, nc_color> &all_area ) { constexpr explosion_neighbors all_neighbors = N_NORTH | N_SOUTH | N_WEST | N_EAST; // We will "shell" the explosion area // Each phase will strip a single layer of points // A layer contains all points that have less than 4 neighbors in cardinal directions // Layers will first be generated, then drawn in inverse order // Start by getting rid of everything except current z-level std::map<point, explosion_tile> neighbors; #if defined(SDLTILES) if( !use_tiles ) { for( const auto &pr : all_area ) { const tripoint relative_point = relative_view_pos( u, pr.first ); if( relative_point.z == 0 ) { point flat_point{ relative_point.x, relative_point.y }; neighbors[flat_point] = explosion_tile{ N_NO_NEIGHBORS, pr.second }; } } } else { // In tiles mode, the coordinates have to be absolute const tripoint view_center = relative_view_pos( u, u.pos() ); for( const auto &pr : all_area ) { const tripoint &pt = pr.first; // Relative point is only used for z level check const tripoint relative_point = relative_view_pos( u, pr.first ); if( relative_point.z == view_center.z ) { point flat_point{ pt.x, pt.y }; neighbors[flat_point] = explosion_tile{ N_NO_NEIGHBORS, pr.second }; } } } #else for( const auto &pr : all_area ) { const tripoint relative_point = relative_view_pos( u, pr.first ); if( relative_point.z == 0 ) { point flat_point{ relative_point.x, relative_point.y }; neighbors[flat_point] = explosion_tile{ N_NO_NEIGHBORS, pr.second }; } } #endif // Searches for a neighbor, sets the neighborhood flag on current point and on the neighbor const auto set_neighbors = [&]( const point &pos, explosion_neighbors &ngh, explosion_neighbors here, explosion_neighbors there ) { if( ( ngh & here ) == N_NO_NEIGHBORS ) { auto other = neighbors.find( pos ); if( other != neighbors.end() ) { ngh = ngh | here; other->second.neighborhood = other->second.neighborhood | there; } } }; // If the point we are about to remove has a neighbor in a given direction // unset that neighbor's flag that our current point is its neighbor const auto unset_neighbor = [&]( const point &pos, const explosion_neighbors ngh, explosion_neighbors here, explosion_neighbors there ) { if( ( ngh & here ) != N_NO_NEIGHBORS ) { auto other = neighbors.find( pos ); if( other != neighbors.end() ) { other->second.neighborhood = ( other->second.neighborhood | there ) ^ there; } } }; // Find all neighborhoods for( auto &pr : neighbors ) { const point &pt = pr.first; explosion_neighbors &ngh = pr.second.neighborhood; set_neighbors( point( pt.x - 1, pt.y ), ngh, N_WEST, N_EAST ); set_neighbors( point( pt.x + 1, pt.y ), ngh, N_EAST, N_WEST ); set_neighbors( point( pt.x, pt.y - 1 ), ngh, N_NORTH, N_SOUTH ); set_neighbors( point( pt.x, pt.y + 1 ), ngh, N_SOUTH, N_NORTH ); } // We need to save the layers because we will draw them in reverse order std::list< std::map<point, explosion_tile> > layers; bool changed = false; while( !neighbors.empty() ) { std::map<point, explosion_tile> layer; changed = false; // Find a layer that can be drawn for( const auto &pr : neighbors ) { if( pr.second.neighborhood != all_neighbors ) { changed = true; layer.insert( pr ); } } if( !changed ) { // An error, but a minor one - let it slide return; } // Remove the layer from the area to process for( const auto &pr : layer ) { const point &pt = pr.first; const explosion_neighbors ngh = pr.second.neighborhood; unset_neighbor( point( pt.x - 1, pt.y ), ngh, N_WEST, N_EAST ); unset_neighbor( point( pt.x + 1, pt.y ), ngh, N_EAST, N_WEST ); unset_neighbor( point( pt.x, pt.y - 1 ), ngh, N_NORTH, N_SOUTH ); unset_neighbor( point( pt.x, pt.y + 1 ), ngh, N_SOUTH, N_NORTH ); neighbors.erase( pr.first ); } layers.push_front( std::move( layer ) ); } #if defined(SDLTILES) if( !use_tiles ) { draw_custom_explosion_curses( *this, layers ); return; } // We need to draw all explosions up to now std::map<point, explosion_tile> combined_layer; for( const auto &layer : layers ) { combined_layer.insert( layer.begin(), layer.end() ); tilecontext->init_custom_explosion_layer( combined_layer ); wrefresh(w_terrain); try_update(); draw_animation_delay(EXPLOSION_MULTIPLIER); } tilecontext->void_custom_explosion(); #else draw_custom_explosion_curses( *this, layers ); #endif }
//Check for any window messages (keypress, paint, mousemove, etc) void CheckMessages() { SDL_Event ev; bool quit = false; while(SDL_PollEvent(&ev)) { switch(ev.type) { case SDL_KEYDOWN: { Uint8 *keystate = SDL_GetKeyState(NULL); // manually handle Alt+F4 for older SDL lib, no big deal if(ev.key.keysym.sym==SDLK_F4 && (keystate[SDLK_RALT] || keystate[SDLK_LALT]) ) { quit = true; break; } else if(ev.key.keysym.sym==SDLK_RSHIFT || ev.key.keysym.sym==SDLK_LSHIFT || ev.key.keysym.sym==SDLK_RCTRL || ev.key.keysym.sym==SDLK_LCTRL || ev.key.keysym.sym==SDLK_RALT || ev.key.keysym.sym==SDLK_LALT) { break; // temporary fix for unwanted keys } else if (ev.key.keysym.unicode != 0) { lastchar = ev.key.keysym.unicode; switch (lastchar){ case 13: //Reroute ENTER key for compatilbity purposes lastchar=10; break; case 8: //Reroute BACKSPACE key for compatilbity purposes lastchar=127; break; } } if(ev.key.keysym.sym==SDLK_LEFT) { lastchar = KEY_LEFT; } else if(ev.key.keysym.sym==SDLK_RIGHT) { lastchar = KEY_RIGHT; } else if(ev.key.keysym.sym==SDLK_UP) { lastchar = KEY_UP; } else if(ev.key.keysym.sym==SDLK_DOWN) { lastchar = KEY_DOWN; } else if(ev.key.keysym.sym==SDLK_PAGEUP) { lastchar = KEY_PPAGE; } else if(ev.key.keysym.sym==SDLK_PAGEDOWN) { lastchar = KEY_NPAGE; } } break; case SDL_QUIT: quit = true; break; } } if (needupdate) try_update(); if(quit) { endwin(); exit(0); } }
void DrawWindow(WINDOW *win) { int i,j,drawx,drawy; char tmp; for (j=0; j<win->height; j++){ if (win->line[j].touched) { needupdate = true; win->line[j].touched=false; for (i=0; i<win->width; i++){ drawx=((win->x+i)*fontwidth); drawy=((win->y+j)*fontheight);//-j; if (((drawx+fontwidth)<=WindowWidth) && ((drawy+fontheight)<=WindowHeight)){ tmp = win->line[j].chars[i]; int FG = win->line[j].FG[i]; int BG = win->line[j].BG[i]; FillRectDIB(drawx,drawy,fontwidth,fontheight,BG); if ( tmp > 0){ OutputChar(tmp, drawx,drawy,1,FG); // } //and this line too. } else if ( tmp < 0 ) { switch (tmp) { case -60://box bottom/top side (horizontal line) HorzLineDIB(drawx,drawy+halfheight,drawx+fontwidth,1,FG); break; case -77://box left/right side (vertical line) VertLineDIB(drawx+halfwidth,drawy,drawy+fontheight,2,FG); break; case -38://box top left HorzLineDIB(drawx+halfwidth,drawy+halfheight,drawx+fontwidth,1,FG); VertLineDIB(drawx+halfwidth,drawy+halfheight,drawy+fontheight,2,FG); break; case -65://box top right HorzLineDIB(drawx,drawy+halfheight,drawx+halfwidth,1,FG); VertLineDIB(drawx+halfwidth,drawy+halfheight,drawy+fontheight,2,FG); break; case -39://box bottom right HorzLineDIB(drawx,drawy+halfheight,drawx+halfwidth,1,FG); VertLineDIB(drawx+halfwidth,drawy,drawy+halfheight+1,2,FG); break; case -64://box bottom left HorzLineDIB(drawx+halfwidth,drawy+halfheight,drawx+fontwidth,1,FG); VertLineDIB(drawx+halfwidth,drawy,drawy+halfheight+1,2,FG); break; case -63://box bottom north T (left, right, up) HorzLineDIB(drawx,drawy+halfheight,drawx+fontwidth,1,FG); VertLineDIB(drawx+halfwidth,drawy,drawy+halfheight,2,FG); break; case -61://box bottom east T (up, right, down) VertLineDIB(drawx+halfwidth,drawy,drawy+fontheight,2,FG); HorzLineDIB(drawx+halfwidth,drawy+halfheight,drawx+fontwidth,1,FG); break; case -62://box bottom south T (left, right, down) HorzLineDIB(drawx,drawy+halfheight,drawx+fontwidth,1,FG); VertLineDIB(drawx+halfwidth,drawy+halfheight,drawy+fontheight,2,FG); break; case -59://box X (left down up right) HorzLineDIB(drawx,drawy+halfheight,drawx+fontwidth,1,FG); VertLineDIB(drawx+halfwidth,drawy,drawy+fontheight,2,FG); break; case -76://box bottom east T (left, down, up) VertLineDIB(drawx+halfwidth,drawy,drawy+fontheight,2,FG); HorzLineDIB(drawx,drawy+halfheight,drawx+halfwidth,1,FG); break; default: // SetTextColor(DC,_windows[w].line[j].chars[i].color.FG); // TextOut(DC,drawx,drawy,&tmp,1); break; } };//switch (tmp) }//(tmp < 0) };//for (i=0;i<_windows[w].width;i++) } };// for (j=0;j<_windows[w].height;j++) win->draw=false; //We drew the window, mark it as so if (needupdate) try_update(); }