/* * Hack -- display monster recall in sub-windows */ static void fix_monster(void) { s32b j; /* Scan windows */ for (j = 0; j < 8; j++) { term *old = Term; /* No window */ if (!angband_term[j]) continue; /* No relevant flags */ if (!flag_exists(&window_flag[j], FLAG_PW_MONSTER)) continue; /* Activate */ Term_activate(angband_term[j]); /* Display monster race info */ if (monster_race_idx) display_roff(monster_race_idx, monster_ego_idx); /* Fresh */ Term_fresh(); /* Restore */ Term_activate(old); } }
/* * Hack -- display object recall in sub-windows */ static void fix_object(void) { s32b j; /* Scan windows */ for (j = 0; j < 8; j++) { term *old = Term; /* No window */ if (!angband_term[j]) continue; /* No relevant flags */ if (!flag_exists(&window_flag[j], FLAG_PW_OBJECT)) continue; /* Activate */ Term_activate(angband_term[j]); /* Clear */ Term_clear(); /* Display object info */ if (tracked_object) if (!object_out_desc(tracked_object, NULL, FALSE, FALSE)) text_out("You see nothing special."); /* Fresh */ Term_fresh(); /* Restore */ Term_activate(old); } }
/** * Redraw the screen * * This command performs various low level updates, clears all the "extra" * windows, does a total redraw of the main window, and requests all of the * interesting updates and redraws that I can think of. * * This command is also used to "instantiate" the results of the user * selecting various things, such as graphics mode, so it must call * the "TERM_XTRA_REACT" hook before redrawing the windows. * */ void do_cmd_redraw(void) { int j; term *old = Term; /* Low level flush */ Term_flush(); /* Reset "inkey()" */ event_signal(EVENT_INPUT_FLUSH); if (character_dungeon) verify_panel(); /* Hack -- React to changes */ Term_xtra(TERM_XTRA_REACT, 0); if (character_dungeon) { /* Combine the pack (later) */ player->upkeep->notice |= (PN_COMBINE); /* Update torch, gear */ player->upkeep->update |= (PU_TORCH | PU_INVEN); /* Update stuff */ player->upkeep->update |= (PU_BONUS | PU_HP | PU_SPELLS); /* Fully update the visuals */ player->upkeep->update |= (PU_FORGET_VIEW | PU_UPDATE_VIEW | PU_MONSTERS); /* Redraw everything */ player->upkeep->redraw |= (PR_BASIC | PR_EXTRA | PR_MAP | PR_INVEN | PR_EQUIP | PR_MESSAGE | PR_MONSTER | PR_OBJECT | PR_MONLIST | PR_ITEMLIST); } /* Clear screen */ Term_clear(); if (character_dungeon) { /* Hack -- update */ handle_stuff(player); /* Place the cursor on the player */ if (0 != character_dungeon) move_cursor_relative(player->px, player->py); } /* Redraw every window */ for (j = 0; j < ANGBAND_TERM_MAX; j++) { if (!angband_term[j]) continue; Term_activate(angband_term[j]); Term_redraw(); Term_fresh(); Term_activate(old); } }
/* * Procedure Redisplay() is called as the result of an Expose event. * Use the redraw callback to do a full redraw */ static void Redisplay(AngbandWidget wnew, XEvent *xev, Region region) { int x1, x2, y1, y2; int i; term_data *old_td = (term_data*)(Term->data); term_data *td = &data[0]; /* Ignore parameter */ (void) region; /* Hack - Find the term to activate */ for (i = 0; i < num_term; i++) { td = &data[i]; /* Have we found it? */ if (td->widget == wnew) break; /* Paranoia: none of the widgets matched */ if (!td) return; } /* Activate the proper Term */ Term_activate(&td->t); /* Find the bounds of the exposed region */ /* * This probably could be obtained from the Region parameter - * but I don't know anything about XAW. */ x1 = (xev->xexpose.x - wnew->angband.internal_border) /wnew->angband.fontwidth; x2 = (xev->xexpose.x + xev->xexpose.width - wnew->angband.internal_border)/wnew->angband.fontwidth; y1 = (xev->xexpose.y - wnew->angband.internal_border) /wnew->angband.fontheight; y2 = (xev->xexpose.y + xev->xexpose.height - wnew->angband.internal_border)/wnew->angband.fontheight; Term_redraw_section(x1, y1, x2, y2); /* Activate the old term */ Term_activate(&old_td->t); #if 0 if (XtHasCallbacks((Widget)widget, XtNredrawCallback) == XtCallbackHasSome) { XtCallCallbacks((Widget)widget, XtNredrawCallback, NULL); } #endif /* 0 */ }
static void Resize_term(AngbandWidget wnew) { int cols, rows, wid, hgt; int ox = wnew->angband.internal_border; int oy = wnew->angband.internal_border; int i; term_data *old_td = (term_data*)(Term->data); term_data *td = &data[0]; /* Hack - Find the term to activate */ for (i = 0; i < num_term; i++) { td = &data[i]; /* Have we found it? */ if (td->widget == wnew) break; /* Paranoia: none of the widgets matched */ if (!td) return; } /* Activate the proper Term */ Term_activate(&td->t); /* Determine "proper" number of rows/cols */ cols = ((wnew->core.width - (ox + ox)) / wnew->angband.fontwidth); rows = ((wnew->core.height - (oy + oy)) / wnew->angband.fontheight); /* Hack -- minimal size */ if (cols < 1) cols = 1; if (rows < 1) rows = 1; if (i == 0) { /* Hack the main window must be at least 80x24 */ if (cols < 80) cols = 80; if (rows < 24) rows = 24; } /* Desired size of window */ wid = cols * wnew->angband.fontwidth + (ox + ox); hgt = rows * wnew->angband.fontheight + (oy + oy); /* Resize the Term (if needed) */ (void) Term_resize(cols, rows); /* Activate the old term */ Term_activate(&old_td->t); }
/* * Do a redraw */ static void react_redraw(Widget widget, XtPointer client_data, XtPointer call_data) { term_data *old_td = (term_data*)(Term->data); term_data *td = (term_data*)client_data; /* Activate the proper Term */ Term_activate(&td->t); /* Request a redraw */ Term_redraw(); /* Activate the old Term */ Term_activate(&old_td->t); }
/* * Prepare this file for Angband usage */ errr init_cap(int argc, char **argv) { term *t = &term_screen_body; /*** Initialize ***/ /* Initialize the screen */ if (init_cap_aux()) return (-1); /* Hack -- Require large screen, or Quit with message */ if ((rows < 24) || (cols < 80)) quit("Screen too small!"); /*** Prepare to play ***/ /* Extract the normal keymap */ keymap_norm_prepare(); /* Extract the game keymap */ keymap_game_prepare(); /* Hack -- activate the game keymap */ keymap_game(); /* Hack -- Do NOT buffer stdout */ setbuf(stdout, NULL); /*** Now prepare the term ***/ /* Initialize the term */ term_init(t, 80, 24, 256); /* Avoid the bottom right corner */ t->icky_corner = TRUE; /* Erase with "white space" */ t->attr_blank = TERM_WHITE; t->char_blank = ' '; /* Set some hooks */ t->init_hook = Term_init_cap; t->nuke_hook = Term_nuke_cap; /* Set some more hooks */ t->text_hook = Term_text_cap; t->wipe_hook = Term_wipe_cap; t->curs_hook = Term_curs_cap; t->xtra_hook = Term_xtra_cap; /* Save the term */ term_screen = t; /* Activate it */ Term_activate(term_screen); /* Success */ return (0); }
static void initPipeTerm(termPipe *pipe, const char *name, term **termTarget) { term *t; t=&pipe->t; if ((pipe->out=initPipe(name))!=NULL) { /* Initialize the term */ term_init(t, 80, 24, 1); /* Special hooks */ t->init_hook = Term_init_pipe_emx; t->nuke_hook = Term_nuke_pipe_emx; /* Add the hooks */ t->text_hook = Term_text_pipe_emx; t->wipe_hook = Term_wipe_pipe_emx; t->curs_hook = Term_curs_pipe_emx; t->xtra_hook = Term_xtra_pipe_emx; /* Save it */ *termTarget = t; /* Activate it */ Term_activate(t); } }
/* * Initialize the VM/CNSconsole. */ errr init_vme(void) { register i; term *t = &term_screen_body; short blank = ' '; static int done = FALSE; /* Paranoia -- Already done */ if (done) return (-1); /* Build a "wiper line" of blank spaces */ for (i = 0; i < 256; i++) wiper[i] = blank; /* Acquire the size of the screen */ rows = 25; cols = 80; /* Initialize the console */ InitConsole(); /* Wipe the screen */ for (i = 0; i < rows; i++) { /* Wipe that row */ memcpy(VirtualScreen + (i*cols), wiper, cols); memset(ScreenAttr + (i*cols), 0xF1, cols); } /* Erase the screen */ ScreenClear(); /* Initialize the term -- very large key buffer */ term_init(t, cols, rows - 1, 1024); /* Prepare the init/nuke hooks */ t->nuke_hook = Term_nuke_vm; /* Connect the hooks */ t->text_hook = Term_text_vm; t->wipe_hook = Term_wipe_vm; t->curs_hook = Term_curs_vm; t->xtra_hook = Term_xtra_vm; /* Save it */ term_screen = t; /* Activate it */ Term_activate(term_screen); /* Done */ done = TRUE; /* Success */ return 0; }
/** * Query ncurses for new screen size and try to resize the GCU terms. */ static void do_gcu_resize(void) { int i, rows, cols, y, x; term *old_t = Term; for (i = 0; i < term_count; i++) { /* Activate the current Term */ Term_activate(&data[i].t); /* If we can resize the curses window, then resize the Term */ get_gcu_term_size(i, &rows, &cols, &y, &x); if (wresize(data[i].win, rows, cols) == OK) Term_resize(cols, rows); /* Activate the old term */ Term_activate(old_t); } do_cmd_redraw(); }
/** * Move the cursor to a given map location. */ static void move_cursor_relative_map(int y, int x) { int ky, kx; term *old; int j; /* Scan windows */ for (j = 0; j < ANGBAND_TERM_MAX; j++) { term *t = angband_term[j]; /* No window */ if (!t) continue; /* No relevant flags */ if (!(window_flag[j] & (PW_MAPS))) continue; /* Location relative to panel */ ky = y - t->offset_y; if (tile_height > 1) ky = tile_height * ky; /* Verify location */ if ((ky < 0) || (ky >= t->hgt)) continue; /* Location relative to panel */ kx = x - t->offset_x; if (tile_width > 1) kx = tile_width * kx; /* Verify location */ if ((kx < 0) || (kx >= t->wid)) continue; /* Go there */ old = Term; Term_activate(t); (void)Term_gotoxy(kx, ky); Term_activate(old); } }
/* * Hack -- display recent messages in sub-windows * * XXX XXX XXX Adjust for width and split messages */ void fix_message(void) { s32b j, i; s32b w, h; s32b x, y; /* Scan windows */ for (j = 0; j < 8; j++) { term *old = Term; /* No window */ if (!angband_term[j]) continue; /* No relevant flags */ if (!flag_exists(&window_flag[j], FLAG_PW_MESSAGE)) continue; /* Activate */ Term_activate(angband_term[j]); /* Get size */ Term_get_size(&w, &h); /* Dump messages */ for (i = 0; i < h; i++) { /* Dump the message on the appropriate line */ display_message(0, (h - 1) - i, strlen(message_str((s16b)i)), message_color((s16b)i), message_str((s16b)i)); /* Cursor */ Term_locate(&x, &y); /* Clear to end of line */ Term_erase(x, y, 255); } /* Fresh */ Term_fresh(); /* Restore */ Term_activate(old); } }
/* * Handle an event */ static void handle_event(Widget widget, XtPointer client_data, XEvent *event, Boolean *continue_to_dispatch) { term_data *old_td = (term_data*)(Term->data); term_data *td = (term_data *)client_data; /* Ignore parameter */ (void) widget; /* Continue to process the event by default */ *continue_to_dispatch = TRUE; /* Activate the Term */ Term_activate(&td->t); switch (event->type) { case KeyPress: { /* Hack -- use old term */ Term_activate(&old_td->t); /* Handle the keypress */ react_keypress(&(event->xkey)); /* We took care of the event */ *continue_to_dispatch = FALSE; break; } /* Oops */ default: { break; } } /* Activate the old term */ Term_activate(&old_td->t); return; }
void pre_turn_refresh(void) { term *old = Term; int j; if (character_dungeon) { /* Redraw map */ player->upkeep->redraw |= (PR_MAP | PR_STATE); player->upkeep->redraw |= (PR_MONLIST | PR_ITEMLIST); handle_stuff(player); move_cursor_relative(player->px, player->py); for (j = 0; j < ANGBAND_TERM_MAX; j++) { if (!angband_term[j]) continue; Term_activate(angband_term[j]); Term_fresh(); } } Term_activate(old); }
/* * Query ncurses for new screen size and try to resize the GCU terms. */ static void do_gcu_resize(void) { int i, rows, cols, y, x; term *old_t = Term; for (i = 0; i < MAX_TERM_DATA; i++) { /* If we're using a big screen, we only care about Term-0 */ if (use_big_screen && i > 0) break; /* Activate the current Term */ Term_activate(&data[i].t); /* If we can resize the curses window, then resize the Term */ get_gcu_term_size(i, &rows, &cols, &y, &x); if (wresize(data[i].win, rows, cols) == OK) Term_resize(cols, rows); /* Activate the old term */ Term_activate(old_t); } do_cmd_redraw(); }
/* * Create a window for the given "term_data" argument. * * Assumes legal arguments. */ static errr term_data_init_gcu(term_data *td, int rows, int cols, int y, int x) { term *t = &td->t; /* Create new window */ td->win = newwin(rows, cols, y, x); /* Check for failure */ if (!td->win) { /* Error */ quit("Failed to setup curses window."); } /* Initialize the term */ term_init(t, cols, rows, 256); /* Avoid bottom right corner */ t->icky_corner = TRUE; /* Erase with "white space" */ t->attr_blank = TERM_WHITE; t->char_blank = ' '; /* Set some hooks */ t->init_hook = Term_init_gcu; t->nuke_hook = Term_nuke_gcu; /* Set some more hooks */ t->text_hook = Term_text_gcu; t->wipe_hook = Term_wipe_gcu; t->curs_hook = Term_curs_gcu; t->xtra_hook = Term_xtra_gcu; /* only if the locale supports Latin-1 will we enable xchar_hook */ if (setlocale(LC_CTYPE, "")) { /* the Latin-1 codeset is ISO-8859-1 */ if (strcmp(nl_langinfo(CODESET), "ISO-8859-1") == 0) t->xchar_hook = Term_xchar_gcu; } /* Save the data */ t->data = td; /* Activate it */ Term_activate(t); /* Success */ return (0); }
static errr term_data_init(term_data *td, int rows, int cols, int y, int x) { term *t = &td->t; /* Make sure the window has a positive size */ if (rows <= 0 || cols <= 0) return (0); assert(x + cols <= COLS); assert(y + rows <= LINES); /* Create a window */ td->win = newwin(rows, cols, y, x); /* Make sure we succeed */ if (!td->win) { plog("Failed to setup curses window."); return (-1); } /* Initialize the term */ term_init(t, cols, rows, 256); /* Avoid the bottom right corner */ t->icky_corner = TRUE; /* Erase with "white space" */ t->attr_blank = TERM_WHITE; t->char_blank = ' '; /* Set some hooks */ t->init_hook = Term_init_gcu; t->nuke_hook = Term_nuke_gcu; /* Set some more hooks */ t->text_hook = Term_text_gcu; t->wipe_hook = Term_wipe_gcu; t->curs_hook = Term_curs_gcu; t->xtra_hook = Term_xtra_gcu; /* Save the data */ t->data = td; /* Activate it */ Term_activate(t); /* Success */ return (0); }
/* * Hook SVGAlib routines into term.c */ errr init_lsl(void) { term *t = &term_screen_body; #ifdef USE_GRAPHICS if (arg_graphics) { use_graphics = TRUE; } #endif /* USE_GRAPHICS */ /* Initialize the term */ term_init(t, 80, 24, 1024); /* The cursor is done via software and needs erasing */ t->soft_cursor = TRUE; t->attr_blank = TERM_DARK; t->char_blank = ' '; /* Add hooks */ t->init_hook = term_init_svgalib; t->nuke_hook = term_nuke_svgalib; t->text_hook = term_text_svgalib; #ifdef USE_GRAPHICS if (use_graphics) { t->pict_hook = term_pict_svgalib; t->higher_pict = TRUE; } #endif /* USE_GRAPHICS */ t->wipe_hook = term_wipe_svgalib; t->curs_hook = term_curs_svgalib; t->xtra_hook = term_xtra_svgalib; /* Save the term */ term_screen = t; /* Activate it */ Term_activate(term_screen); return (0); }
/* * Create a window for the given "term_data" argument. */ static errr term_data_init_gcu(term_data *td, int rows, int cols, int y, int x) { term *t = &td->t; /* Check window size */ if (rows <= 0 || cols <= 0) return (0); /* Create new window */ td->win = newwin(rows, cols, y, x); /* Check for failure */ if (!td->win) { /* Error */ quit("Failed to setup curses window."); } /* Initialize the term */ term_init(t, cols, rows, 256); /* Avoid bottom right corner */ t->icky_corner = TRUE; /* Erase with "black space" */ t->attr_blank = TERM_DARK; t->char_blank = ' '; /* Set some hooks */ t->init_hook = Term_init_gcu; t->nuke_hook = Term_nuke_gcu; /* Set some more hooks */ t->text_hook = Term_text_gcu; t->wipe_hook = Term_wipe_gcu; t->curs_hook = Term_curs_gcu; t->xtra_hook = Term_xtra_gcu; /* Save the data */ t->data = td; /* Activate it */ Term_activate(t); /* Success */ return (0); }
static void init_windows(void) { int i; term *t = &data; /* Main window */ term_data_link(t); angband_term[0] = t; /* No extra Term's required */ for (i = 1; i < 8; i++) { angband_term[i] = NULL; } Term_activate(t); }
/* * Prepare "term.c" to use "USE_EMX" built-in faked video library */ errr init_emx(void) { int i; /* Initialize the windows */ emx_init_term(&term_screen_aga[0], NULL, &angband_term[0], 0); for (i = 1; i < MAX_TERM_DATA; ++i) { emx_init_term(&term_screen_aga[i], term_screen_aga[0].instance, &angband_term[i], i); } /* Activate main window */ Term_activate(angband_term[0]); /* Success */ return (0); }
/** * Create a window for the given "term_data" argument. * * Assumes legal arguments. */ static errr term_data_init_gcu(term_data *td, int rows, int cols, int y, int x) { term *t = &td->t; /* Create new window */ td->win = newwin(rows, cols, y, x); /* Check for failure */ if (!td->win) quit("Failed to setup curses window."); /* Initialize the term */ term_init(t, cols, rows, 256); /* Avoid bottom right corner */ t->icky_corner = TRUE; /* Erase with "white space" */ t->attr_blank = COLOUR_WHITE; t->char_blank = ' '; /* Differentiate between BS/^h, Tab/^i, etc. */ t->complex_input = TRUE; /* Set some hooks */ t->init_hook = Term_init_gcu; t->nuke_hook = Term_nuke_gcu; /* Set some more hooks */ t->text_hook = Term_text_gcu; t->wipe_hook = Term_wipe_gcu; t->curs_hook = Term_curs_gcu; t->xtra_hook = Term_xtra_gcu; /* Save the data */ t->data = td; /* Activate it */ Term_activate(t); /* Success */ return (0); }
/** * Redraw a term when it is resized */ void redraw_window(void) { /* Only if the dungeon exists */ if (!character_dungeon) return; /* Hack - Activate term zero for the redraw */ Term_activate(&term_screen[0]); /* Hack -- react to changes */ Term_xtra(TERM_XTRA_REACT, 0); /* Hack -- update */ handle_stuff(p_ptr); /* Redraw */ Term_redraw(); /* Refresh */ Term_fresh(); }
/* * Prepare "term.c" to use "USE_EMX" built-in video library */ errr init_emx(void) { int i; term *t; /* Initialize the pipe windows */ for (i = MAX_TERM_DATA-1; i > 0; --i) { const char *name = angband_term_name[i]; initPipeTerm(&term_screen_aga[i], name, &angband_term[i]); } /* Initialize main window */ t = &term_screen_aga[0].t; /* Initialize the term -- big key buffer */ term_init(t, 80, 24, 1024); /* Special hooks */ t->init_hook = Term_init_emx; t->nuke_hook = Term_nuke_emx; /* Add the hooks */ t->text_hook = Term_text_emx; t->wipe_hook = Term_wipe_emx; t->curs_hook = Term_curs_emx; t->xtra_hook = Term_xtra_emx; /* Save it */ angband_term[0] = t; /* Activate it */ Term_activate(t); /* Success */ return (0); }
/* * Get a keypress from the user. * * This function recognizes a few "global parameters". These are variables * which, if set to TRUE before calling this function, will have an effect * on this function, and which are always reset to FALSE by this function * before this function returns. Thus they function just like normal * parameters, except that most calls to this function can ignore them. * * If "inkey_xtra" is TRUE, then all pending keypresses will be flushed. * This is set by flush(), which doesn't actually flush anything itself * but uses that flag to trigger delayed flushing. * * If "inkey_scan" is TRUE, then we will immediately return "zero" if no * keypress is available, instead of waiting for a keypress. * * If "inkey_flag" is TRUE, then we are waiting for a command in the main * map interface, and we shouldn't show a cursor. * * If we are waiting for a keypress, and no keypress is ready, then we will * refresh (once) the window which was active when this function was called. * * Note that "back-quote" is automatically converted into "escape" for * convenience on machines with no "escape" key. * * If "angband_term[0]" is not active, we will make it active during this * function, so that the various "main-xxx.c" files can assume that input * is only requested (via "Term_inkey()") when "angband_term[0]" is active. * * Mega-Hack -- This function is used as the entry point for clearing the * "signal_count" variable, and of the "character_saved" variable. * * Mega-Hack -- Note the use of "inkey_hack" to allow the "Borg" to steal * control of the keyboard from the user. */ ui_event inkey_ex(void) { bool cursor_state; ui_event kk; ui_event ke = EVENT_EMPTY; bool done = FALSE; term *old = Term; /* Delayed flush */ if (inkey_xtra) { Term_flush(); inkey_next = NULL; inkey_xtra = FALSE; } /* Hack -- Use the "inkey_next" pointer */ if (inkey_next && inkey_next->code) { /* Get next character, and advance */ ke.key = *inkey_next++; /* Cancel the various "global parameters" */ inkey_flag = FALSE; inkey_scan = 0; /* Accept result */ return (ke); } /* Forget pointer */ inkey_next = NULL; #ifdef ALLOW_BORG /* Mega-Hack -- Use the special hook */ if (inkey_hack) { ke.key = (*inkey_hack)(inkey_xtra); if (ke.key.type != EVT_NONE) { /* Cancel the various "global parameters" */ inkey_flag = FALSE; inkey_scan = 0; ke.type = EVT_KBRD; /* Accept result */ return (ke); } } #endif /* ALLOW_BORG */ /* Get the cursor state */ (void)Term_get_cursor(&cursor_state); /* Show the cursor if waiting, except sometimes in "command" mode */ if (!inkey_scan && (!inkey_flag || character_icky)) (void)Term_set_cursor(TRUE); /* Hack -- Activate main screen */ Term_activate(term_screen); /* Get a key */ while (ke.type == EVT_NONE) { /* Hack -- Handle "inkey_scan == SCAN_INSTANT */ if (inkey_scan == SCAN_INSTANT && (0 != Term_inkey(&kk, FALSE, FALSE))) break; /* Hack -- Flush output once when no key ready */ if (!done && (0 != Term_inkey(&kk, FALSE, FALSE))) { /* Hack -- activate proper term */ Term_activate(old); /* Flush output */ Term_fresh(); /* Hack -- activate main screen */ Term_activate(term_screen); /* Mega-Hack -- reset saved flag */ character_saved = FALSE; /* Mega-Hack -- reset signal counter */ signal_count = 0; /* Only once */ done = TRUE; } /* Get a key (see above) */ ke = inkey_aux(inkey_scan); /* Handle mouse buttons */ if ((ke.type == EVT_MOUSE) && (OPT(mouse_buttons))) { /* Check to see if we've hit a button */ /* Assuming text buttons here for now - this would have to * change for GUI buttons */ char key = button_get_key(ke.mouse.x, ke.mouse.y); if (key) { /* Rewrite the event */ /* XXXmacro button implementation needs updating */ ke.type = EVT_BUTTON; ke.key.code = key; ke.key.mods = 0; /* Done */ break; } } /* Treat back-quote as escape */ if (ke.key.code == '`') ke.key.code = ESCAPE; } /* Hack -- restore the term */ Term_activate(old); /* Restore the cursor */ Term_set_cursor(cursor_state); /* Cancel the various "global parameters" */ inkey_flag = FALSE; inkey_scan = 0; /* Return the keypress */ return (ke); }
/* * Prepare "S-Lang" for use by the file "z-term.c" * Installs the "hook" functions defined above */ errr init_sla(int argc, char **argv) { int err; term *t = &term_screen_body; /* Unused parameters */ (void)argc; (void)argv; /* Block signals, so signals cannot confuse the setup */ SLsig_block_signals(); /* Initialize, check for errors */ err = (SLang_init_tty(-1, TRUE, 0) == -1); /* Quit on error */ if (err) quit("SLang initialization failed"); /* Get terminal info */ SLtt_get_terminfo(); #ifdef HANDLE_SIGNALS /* Allow keyboard generated suspend signal (on Unix, ^Z) */ SLtty_set_suspend_state(TRUE); /* Instead of signal(), use sigaction():SA_RESTART via SLsignal() */ signal_aux = SLsignal; #endif /* Initialize some more */ if (SLsmg_init_smg() == -1) { SLang_reset_tty(); quit("Could not get virtual display memory"); } /* Check we have enough screen. */ err = ((SLtt_Screen_Rows < 24) || (SLtt_Screen_Cols < 80)); /* Quit with message */ if (err) { SLsmg_reset_smg(); SLang_reset_tty(); quit("SLang screen must be at least 80x24"); } /* Now let's go for a little bit of color! */ err = !has_colors(); /* Do we have color available? */ can_use_color = !err; /* Init the Color-pairs and set up a translation table */ /* If the terminal has enough colors */ /* Color-pair 0 is *always* WHITE on BLACK */ /* XXX XXX XXX See "main-gcu.c" for proper method */ /* Only do this on color machines */ if (can_use_color) { /* Prepare the color pairs */ init_pair(1, COLOR_RED, COLOR_BLACK); init_pair(2, COLOR_GREEN, COLOR_BLACK); init_pair(3, COLOR_YELLOW, COLOR_BLACK); init_pair(4, COLOR_BLUE, COLOR_BLACK); init_pair(5, COLOR_MAGENTA, COLOR_BLACK); init_pair(6, COLOR_CYAN, COLOR_BLACK); init_pair(7, COLOR_BLACK, COLOR_BLACK); init_pair(9, COLOR_BRED, COLOR_BLACK); init_pair(10, COLOR_BGREEN, COLOR_BLACK); init_pair(11, COLOR_BYELLOW, COLOR_BLACK); init_pair(12, COLOR_BBLUE, COLOR_BLACK); init_pair(13, COLOR_BMAGENTA, COLOR_BLACK); init_pair(14, COLOR_BCYAN, COLOR_BLACK); init_pair(15, COLOR_BBLACK, COLOR_BLACK); /* Prepare the color table */ colortable[0] = 7; /* Black */ colortable[1] = 0; /* White */ colortable[2] = 6; /* Grey XXX */ colortable[3] = 11; /* Orange XXX */ colortable[4] = 1; /* Red */ colortable[5] = 2; /* Green */ colortable[6] = 4; /* Blue */ colortable[7] = 3; /* Brown */ colortable[8] = 15; /* Dark-grey XXX */ colortable[9] = 14; /* Light-grey XXX */ colortable[10] = 5; /* Purple */ colortable[11] = 11; /* Yellow */ colortable[12] = 9; /* Light Red */ colortable[13] = 10; /* Light Green */ colortable[14] = 12; /* Light Blue */ colortable[15] = 3; /* Light Brown XXX */ } /* Done with blocking */ SLsig_unblock_signals(); /* Initialize the term */ term_init(t, 80, 24, 64); /* Stick in some hooks */ t->nuke_hook = Term_nuke_sla; t->init_hook = Term_init_sla; /* Stick in some more hooks */ t->xtra_hook = Term_xtra_sla; t->curs_hook = Term_curs_sla; t->wipe_hook = Term_wipe_sla; t->text_hook = Term_text_sla; /* Save the term */ term_screen = t; /* Activate it */ Term_activate(t); /* Success */ return 0; }
/* * Prepare "curses" for use by the file "z-term.c" * * Installs the "hook" functions defined above, and then activates * the main screen "term", which clears the screen and such things. * * Someone should really check the semantics of "initscr()" */ errr init_gcu(int argc, char **argv) { int i; int num_term = MAX_TERM_DATA, next_win = 0; bool use_big_screen = FALSE; /* Parse args */ for (i = 1; i < argc; i++) { if (prefix(argv[i], "-b")) { use_big_screen = TRUE; continue; } plog_fmt("Ignoring option: %s", argv[i]); } /* Extract the normal keymap */ keymap_norm_prepare(); /* Initialize */ if (initscr() == NULL) return (-1); /* Activate hooks */ quit_aux = hook_quit; core_aux = hook_quit; /* Require standard size screen */ if ((LINES < 24) || (COLS < 80)) { quit(GAME_NAME " needs at least an 80x24 'curses' screen"); } #ifdef USE_GRAPHICS /* Set graphics flag */ use_graphics = arg_graphics; #endif #ifdef A_COLOR /*** Init the Color-pairs and set up a translation table ***/ /* Do we have color, and enough color, available? */ can_use_color = ((start_color() != ERR) && has_colors() && (COLORS >= 8) && (COLOR_PAIRS >= 8)); #ifdef REDEFINE_COLORS /* Can we change colors? */ can_fix_color = (can_use_color && can_change_color() && (COLORS >= 16) && (COLOR_PAIRS > 8)); #endif /* Attempt to use customized colors */ if (can_fix_color) { /* Prepare the color pairs */ for (i = 1; i <= 8; i++) { /* Reset the color */ if (init_pair(i, i - 1, 0) == ERR) { quit("Color pair init failed"); } /* Set up the colormap */ colortable[i - 1] = (COLOR_PAIR(i) | A_NORMAL); colortable[i + 7] = (COLOR_PAIR(i) | A_BRIGHT); } /* Take account of "gamma correction" XXX XXX XXX */ /* Prepare the "Angband Colors" */ Term_xtra_gcu_react(); } /* Attempt to use colors */ else if (can_use_color) { /* Color-pair 0 is *always* WHITE on BLACK */ /* Prepare the color pairs */ init_pair(1, COLOR_RED, COLOR_BLACK); init_pair(2, COLOR_GREEN, COLOR_BLACK); init_pair(3, COLOR_YELLOW, COLOR_BLACK); init_pair(4, COLOR_BLUE, COLOR_BLACK); init_pair(5, COLOR_MAGENTA, COLOR_BLACK); init_pair(6, COLOR_CYAN, COLOR_BLACK); init_pair(7, COLOR_BLACK, COLOR_BLACK); /* Prepare the "Angband Colors" -- Bright white is too bright */ colortable[0] = (COLOR_PAIR(7) | A_NORMAL); /* Black */ colortable[1] = (COLOR_PAIR(0) | A_NORMAL); /* White */ colortable[2] = (COLOR_PAIR(6) | A_NORMAL); /* Grey XXX */ colortable[3] = (COLOR_PAIR(1) | A_BRIGHT); /* Orange XXX */ colortable[4] = (COLOR_PAIR(1) | A_NORMAL); /* Red */ colortable[5] = (COLOR_PAIR(2) | A_NORMAL); /* Green */ colortable[6] = (COLOR_PAIR(4) | A_NORMAL); /* Blue */ colortable[7] = (COLOR_PAIR(3) | A_NORMAL); /* Umber */ colortable[8] = (COLOR_PAIR(7) | A_BRIGHT); /* Dark-grey XXX */ colortable[9] = (COLOR_PAIR(6) | A_BRIGHT); /* Light-grey XXX */ colortable[10] = (COLOR_PAIR(5) | A_NORMAL); /* Purple */ colortable[11] = (COLOR_PAIR(3) | A_BRIGHT); /* Yellow */ colortable[12] = (COLOR_PAIR(5) | A_BRIGHT); /* Light Red XXX */ colortable[13] = (COLOR_PAIR(2) | A_BRIGHT); /* Light Green */ colortable[14] = (COLOR_PAIR(4) | A_BRIGHT); /* Light Blue */ colortable[15] = (COLOR_PAIR(3) | A_NORMAL); /* Light Umber XXX */ } #endif /*** Low level preparation ***/ #ifdef USE_GETCH /* Paranoia -- Assume no waiting */ nodelay(stdscr, FALSE); #endif /* Prepare */ cbreak(); noecho(); nonl(); /* Extract the game keymap */ keymap_game_prepare(); /*** Now prepare the term(s) ***/ /* Big screen -- one big term */ if (use_big_screen) { /* Create a term */ term_data_init_gcu(&data[0], LINES, COLS, 0, 0); /* Remember the term */ windows[0].term = &data[0].t; } /* No big screen -- create as many term windows as possible */ else { /* Create several terms */ for (i = 0; i < num_term; i++) { int rows, cols, y, x; /* Decide on size and position */ switch (i) { /* Upper left */ case 0: { rows = 24; cols = 80; y = x = 0; break; } /* Lower left */ case 1: { rows = LINES - 25; cols = 80; y = 25; x = 0; break; } /* Upper right */ case 2: { rows = 24; cols = COLS - 81; y = 0; x = 81; break; } /* Lower right */ case 3: { rows = LINES - 25; cols = COLS - 81; y = 25; x = 81; break; } /* XXX */ default: { rows = cols = y = x = 0; break; } } /* Skip non-existant windows */ if (rows <= 0 || cols <= 0) continue; /* Create a term */ term_data_init_gcu(&data[next_win], rows, cols, y, x); /* Remember the term */ windows[next_win].term = &data[next_win].t; /* One more window */ next_win++; } } /* Activate the "Angband" window screen */ Term_activate(&data[0].t); /* Remember the active screen */ term_screen = &data[0].t; /* Success */ return (0); }
/* * Initialization function for an X Athena Widget module to Angband * * We should accept "-d<dpy>" requests in the "argv" array. XXX XXX XXX */ errr init_xaw(int argc, char *argv[]) { int i; Widget topLevel; Display *dpy; cptr dpy_name = ""; #ifdef USE_GRAPHICS char filename[1024]; int pict_wid = 0; int pict_hgt = 0; #ifdef USE_TRANSPARENCY char *TmpData; #endif /* USE_TRANSPARENCY */ #endif /* USE_GRAPHICS */ /* Parse args */ for (i = 1; i < argc; i++) { if (prefix(argv[i], "-d")) { dpy_name = &argv[i][2]; continue; } #ifdef USE_GRAPHICS if (prefix(argv[i], "-s")) { smoothRescaling = FALSE; continue; } #endif /* USE_GRAPHICS */ if (prefix(argv[i], "-n")) { num_term = atoi(&argv[i][2]); if (num_term > MAX_TERM_DATA) num_term = MAX_TERM_DATA; else if (num_term < 1) num_term = 1; continue; } plog_fmt("Ignoring option: %s", argv[i]); } /* Attempt to open the local display */ dpy = XOpenDisplay(dpy_name); /* Failure -- assume no X11 available */ if (!dpy) return (-1); /* Close the local display */ XCloseDisplay(dpy); #ifdef USE_XAW_LANG /* Support locale processing */ XtSetLanguageProc(NULL, NULL, NULL); #endif /* USE_XAW_LANG */ /* Initialize the toolkit */ topLevel = XtAppInitialize(&appcon, "Angband", NULL, 0, &argc, argv, fallback, NULL, 0); /* Initialize the windows */ for (i = 0; i < num_term; i++) { term_data *td = &data[i]; term_data_init(td, topLevel, 1024, termNames[i], (i == 0) ? specialArgs : defaultArgs, TERM_FALLBACKS, i); angband_term[i] = Term; } /* Activate the "Angband" window screen */ Term_activate(&data[0].t); /* Raise the "Angband" window */ term_raise(&data[0]); #ifdef USE_GRAPHICS /* Try graphics */ if (arg_graphics) { /* Try the "16x16.bmp" file */ path_build(filename, 1024, ANGBAND_DIR_XTRA, "graf/16x16.bmp"); /* Use the "16x16.bmp" file if it exists */ if (0 == fd_close(fd_open(filename, O_RDONLY))) { /* Use graphics */ use_graphics = TRUE; use_transparency = TRUE; pict_wid = pict_hgt = 16; ANGBAND_GRAF = "new"; } else { /* Try the "8x8.bmp" file */ path_build(filename, 1024, ANGBAND_DIR_XTRA, "graf/8x8.bmp"); /* Use the "8x8.bmp" file if it exists */ if (0 == fd_close(fd_open(filename, O_RDONLY))) { /* Use graphics */ use_graphics = TRUE; pict_wid = pict_hgt = 8; ANGBAND_GRAF = "old"; } } } /* Load graphics */ if (use_graphics) { /* Hack -- Get the Display */ term_data *td = &data[0]; Widget widget = (Widget)(td->widget); Display *dpy = XtDisplay(widget); XImage *tiles_raw; /* Load the graphical tiles */ tiles_raw = ReadBMP(dpy, filename); /* Initialize the windows */ for (i = 0; i < num_term; i++) { term_data *td = &data[i]; term *t = &td->t; t->pict_hook = Term_pict_xaw; t->higher_pict = TRUE; /* Resize tiles */ td->widget->angband.tiles = ResizeImage(dpy, tiles_raw, pict_wid, pict_hgt, td->widget->angband.fontwidth, td->widget->angband.fontheight); } #ifdef USE_TRANSPARENCY /* Initialize the transparency temp storage*/ for (i = 0; i < num_term; i++) { term_data *td = &data[i]; int ii, jj; int depth = DefaultDepth(dpy, DefaultScreen(dpy)); Visual *visual = DefaultVisual(dpy, DefaultScreen(dpy)); int total; /* Determine total bytes needed for image */ ii = 1; jj = (depth - 1) >> 2; while (jj >>= 1) ii <<= 1; total = td->widget->angband.fontwidth * td->widget->angband.fontheight * ii; TmpData = (char *)malloc(total); td->widget->angband.TmpImage = XCreateImage(dpy, visual,depth, ZPixmap, 0, TmpData, td->widget->angband.fontwidth, td->widget->angband.fontheight, 8, 0); } #endif /* USE_TRANSPARENCY */ /* Free tiles_raw? XXX XXX */ } #endif /* USE_GRAPHICS */ /* Success */ return (0); }
/* * Initialize a term_data */ static errr term_data_init(term_data *td, Widget topLevel, int key_buf, String name, ArgList widget_arg, Cardinal widget_arg_no, int i) { Widget parent; term *t = &td->t; int cols = 80; int rows = 24; char buf[80]; cptr str; int val; /* Create the shell widget */ parent = XtCreatePopupShell(name, topLevelShellWidgetClass, topLevel, NULL, 0); /* Window specific cols */ sprintf(buf, "ANGBAND_X11_COLS_%d", i); str = getenv(buf); val = (str != NULL) ? atoi(str) : -1; if (val > 0) cols = val; /* Window specific rows */ sprintf(buf, "ANGBAND_X11_ROWS_%d", i); str = getenv(buf); val = (str != NULL) ? atoi(str) : -1; if (val > 0) rows = val; /* Hack the main window must be at least 80x24 */ if (i == 0) { if (cols < 80) cols = 80; if (rows < 24) rows = 24; } /* Reset the initial size */ widget_arg[0].value = rows; widget_arg[1].value = cols; /* Create the interior widget */ td->widget = (AngbandWidget) XtCreateManagedWidget(name, angbandWidgetClass, parent, widget_arg, widget_arg_no); /* Initialize the term (full size) */ term_init(t, cols, rows, key_buf); /* Use a "soft" cursor */ t->soft_cursor = TRUE; /* Erase with "white space" */ t->attr_blank = TERM_WHITE; t->char_blank = ' '; /* Hooks */ t->xtra_hook = Term_xtra_xaw; t->curs_hook = Term_curs_xaw; t->wipe_hook = Term_wipe_xaw; t->text_hook = Term_text_xaw; /* Save the data */ t->data = td; /* Register the keypress event handler */ XtAddEventHandler((Widget)td->widget, KeyPressMask, False, (XtEventHandler) handle_event, td); /* Redraw callback */ XtAddCallback((Widget)td->widget, XtNredrawCallback, react_redraw, td); /* Realize the widget */ XtRealizeWidget(parent); /* Make it visible */ XtPopup(parent, XtGrabNone); /* Activate (important) */ Term_activate(t); Resize_term(td->widget); return 0; }
/** * Prepare "curses" for use by the file "ui-term.c" * * Installs the "hook" functions defined above, and then activates * the main screen "term", which clears the screen and such things. * * Someone should really check the semantics of "initscr()" */ errr init_gcu(int argc, char **argv) { int i; int rows, cols, y, x; int next_win = 0; /* Initialize info about terminal capabilities */ termtype = getenv("TERM"); loaded_terminfo = termtype && tgetent(0, termtype) == 1; /* Parse args */ for (i = 1; i < argc; i++) { if (prefix(argv[i], "-b")) { term_count = 1; } else if (prefix(argv[i], "-B")) { bold_extended = TRUE; } else if (prefix(argv[i], "-a")) { ascii_walls = TRUE; } else if (prefix(argv[i], "-n")) { term_count = atoi(&argv[i][2]); if (term_count > MAX_TERM_DATA) term_count = MAX_TERM_DATA; else if (term_count < 1) term_count = 1; } else { plog_fmt("Ignoring option: %s", argv[i]); } } /* Extract the normal keymap */ keymap_norm_prepare(); /* We do it like this to prevent a link error with curseses that * lack ESCDELAY. */ if (!getenv("ESCDELAY")) putenv("ESCDELAY=20"); /* Initialize */ if (initscr() == NULL) return (-1); /* Activate hooks */ quit_aux = hook_quit; /* Require standard size screen */ if (LINES < MIN_TERM0_LINES || COLS < MIN_TERM0_COLS) quit("Angband needs at least an 80x24 'curses' screen"); #ifdef A_COLOR /* Do we have color, and enough color, available? */ can_use_color = ((start_color() != ERR) && has_colors() && (COLORS >= 8) && (COLOR_PAIRS >= 8)); #ifdef HAVE_USE_DEFAULT_COLORS /* Should we use curses' "default color" */ if (use_default_colors() == OK) bg_color = -1; #endif /* Attempt to use colors */ if (can_use_color) { /* Prepare the color pairs */ /* PAIR_WHITE (pair 0) is *always* WHITE on BLACK */ init_pair(PAIR_RED, COLOR_RED, bg_color); init_pair(PAIR_GREEN, COLOR_GREEN, bg_color); init_pair(PAIR_YELLOW, COLOR_YELLOW, bg_color); init_pair(PAIR_BLUE, COLOR_BLUE, bg_color); init_pair(PAIR_MAGENTA, COLOR_MAGENTA, bg_color); init_pair(PAIR_CYAN, COLOR_CYAN, bg_color); init_pair(PAIR_BLACK, COLOR_BLACK, bg_color); /* Prepare the colors */ colortable[COLOUR_DARK] = (COLOR_PAIR(PAIR_BLACK)); colortable[COLOUR_WHITE] = (COLOR_PAIR(PAIR_WHITE) | A_BRIGHT); colortable[COLOUR_SLATE] = (COLOR_PAIR(PAIR_WHITE)); colortable[COLOUR_ORANGE] = (COLOR_PAIR(PAIR_YELLOW) | A_BRIGHT); colortable[COLOUR_RED] = (COLOR_PAIR(PAIR_RED)); colortable[COLOUR_GREEN] = (COLOR_PAIR(PAIR_GREEN)); colortable[COLOUR_BLUE] = (COLOR_PAIR(PAIR_BLUE)); colortable[COLOUR_UMBER] = (COLOR_PAIR(PAIR_YELLOW)); colortable[COLOUR_L_DARK] = (COLOR_PAIR(PAIR_BLACK) | A_BRIGHT); colortable[COLOUR_L_WHITE] = (COLOR_PAIR(PAIR_WHITE)); colortable[COLOUR_L_PURPLE] = (COLOR_PAIR(PAIR_MAGENTA)); colortable[COLOUR_YELLOW] = (COLOR_PAIR(PAIR_YELLOW) | A_BRIGHT); colortable[COLOUR_L_RED] = (COLOR_PAIR(PAIR_MAGENTA) | A_BRIGHT); colortable[COLOUR_L_GREEN] = (COLOR_PAIR(PAIR_GREEN) | A_BRIGHT); colortable[COLOUR_L_BLUE] = (COLOR_PAIR(PAIR_BLUE) | A_BRIGHT); colortable[COLOUR_L_UMBER] = (COLOR_PAIR(PAIR_YELLOW)); colortable[COLOUR_PURPLE] = (COLOR_PAIR(PAIR_MAGENTA)); colortable[COLOUR_VIOLET] = (COLOR_PAIR(PAIR_MAGENTA)); colortable[COLOUR_TEAL] = (COLOR_PAIR(PAIR_CYAN)); colortable[COLOUR_MUD] = (COLOR_PAIR(PAIR_YELLOW)); colortable[COLOUR_L_YELLOW] = (COLOR_PAIR(PAIR_YELLOW | A_BRIGHT)); colortable[COLOUR_MAGENTA] = (COLOR_PAIR(PAIR_MAGENTA | A_BRIGHT)); colortable[COLOUR_L_TEAL] = (COLOR_PAIR(PAIR_CYAN) | A_BRIGHT); colortable[COLOUR_L_VIOLET] = (COLOR_PAIR(PAIR_MAGENTA) | A_BRIGHT); colortable[COLOUR_L_PINK] = (COLOR_PAIR(PAIR_MAGENTA) | A_BRIGHT); colortable[COLOUR_MUSTARD] = (COLOR_PAIR(PAIR_YELLOW)); colortable[COLOUR_BLUE_SLATE] = (COLOR_PAIR(PAIR_BLUE)); colortable[COLOUR_DEEP_L_BLUE] = (COLOR_PAIR(PAIR_BLUE)); } #endif /* Paranoia -- Assume no waiting */ nodelay(stdscr, FALSE); /* Prepare */ cbreak(); noecho(); nonl(); /* Tell curses to rewrite escape sequences to KEY_UP and friends */ keypad(stdscr, TRUE); /* Extract the game keymap */ keymap_game_prepare(); /* Now prepare the term(s) */ for (i = 0; i < term_count; i++) { /* Get the terminal dimensions; if the user asked for a big screen * then we'll put the whole screen in term 0; otherwise we'll divide * it amongst the available terms */ get_gcu_term_size(i, &rows, &cols, &y, &x); /* Skip non-existant windows */ if (rows <= 0 || cols <= 0) continue; /* Create a term */ term_data_init_gcu(&data[next_win], rows, cols, y, x); /* Remember the term */ angband_term[next_win] = &data[next_win].t; /* One more window */ next_win++; } /* Activate the "Angband" window screen */ Term_activate(&data[0].t); /* Remember the active screen */ term_screen = &data[0].t; /* Success */ return (0); }