/**************************************************************************** * Copyright (c) 2017 Free Software Foundation, Inc. * * * * Permission is hereby granted, free of charge, to any person obtaining a * * copy of this software and associated documentation files (the * * "Software"), to deal in the Software without restriction, including * * without limitation the rights to use, copy, modify, merge, publish, * * distribute, distribute with modifications, sublicense, and/or sell * * copies of the Software, and to permit persons to whom the Software is * * furnished to do so, subject to the following conditions: * * * * The above copyright notice and this permission notice shall be included * * in all copies or substantial portions of the Software. * * * * THE SOFTWARE IS PROVIDED "AS IS", WITHOUT WARRANTY OF ANY KIND, EXPRESS * * OR IMPLIED, INCLUDING BUT NOT LIMITED TO THE WARRANTIES OF * * MERCHANTABILITY, FITNESS FOR A PARTICULAR PURPOSE AND NONINFRINGEMENT. * * IN NO EVENT SHALL THE ABOVE COPYRIGHT HOLDERS BE LIABLE FOR ANY CLAIM, * * DAMAGES OR OTHER LIABILITY, WHETHER IN AN ACTION OF CONTRACT, TORT OR * * OTHERWISE, ARISING FROM, OUT OF OR IN CONNECTION WITH THE SOFTWARE OR * * THE USE OR OTHER DEALINGS IN THE SOFTWARE. * * * * Except as contained in this notice, the name(s) of the above copyright * * holders shall not be used in advertising or otherwise to promote the * * sale, use or other dealings in this Software without prior written * * authorization. * ****************************************************************************/ /* * $Id: demo_new_pair.c,v 1.13 2017/04/15 17:36:00 tom Exp $ * * Demonstrate the alloc_pair() function. */ #include #include #include #if HAVE_ALLOC_PAIR && USE_WIDEC_SUPPORT #include #include #include #define MAX_BITS 8 /* all but A_ALTCHARSET */ #define MAX_ATTR ((1< 0) { if (now < COLOR_PAIRS) { int fg, bg; our_content(now, &fg, &bg); if (init_pair((short) now, (short) fg, (short) bg) != OK) now = ERR; } else { now %= COLOR_PAIRS; } result = now; } return result; } static time_t now(void) { return time((time_t *) 0); } static void usage(void) { static const char *msg[] = { "Usage: demo_new_pair [options]", "", "Repeatedly print using all possible color combinations.", "", "Options:", " -i use init_pair rather than alloc_pair", " -p start in paged-mode", " -s start in single-step mode", " -w print a wide-character cell", }; unsigned n; for (n = 0; n < SIZEOF(msg); ++n) { fprintf(stderr, "%s\n", msg[n]); } ExitProgram(EXIT_FAILURE); } #define use_pages() \ paged_mode = TRUE, single_mode = TRUE #define use_single() \ paged_mode = FALSE, single_mode = TRUE #define update_modes() \ scrollok(stdscr, !paged_mode); \ nodelay(stdscr, !single_mode || paged_mode) int main(int argc, char *argv[]) { static const char *help[] = { "This program iterates over the possible color combinations,", "allocating or initializing color pairs. For best results,", "choose screen-width dividing evenly into the number of colors,", "e.g.,", "", " 32x64,32x128 256 colors", " 24x44,24x88 88 colors", " 32x64,24x128 16 colors", "", "Keys:", " c toggle between coloring and de-coloring cells", " p show one page at a time", " s show one character at a time", " display char/page without pausing", " v/V cycle through video attributes", " w toggle between \"#\" and a double-width equivalent", " ? print this screen (exit on any character).", "", "To exit this program, press ^Q, ^[ or \"q\".", 0 }; bool done = FALSE; bool clobber = FALSE; bool hascolor = FALSE; bool use_init = FALSE; bool use_wide = FALSE; bool paged_mode = FALSE; bool single_mode = FALSE; int video_mode = 0; int current; int ch; wchar_t wch[2]; time_t start = now(); long total_cells = 0; FILE *output = 0; setlocale(LC_ALL, ""); while ((ch = getopt(argc, argv, "ipsw")) != -1) { switch (ch) { case 'i': use_init = TRUE; break; case 'p': use_pages(); break; case 's': use_single(); break; case 'w': use_wide = TRUE; break; default: usage(); break; } } if (isatty(fileno(stderr))) { output = stderr; } else if ((ch = open("/dev/tty", O_WRONLY)) != 0) { output = fdopen(ch, "w"); } else { fprintf(stderr, "cannot open terminal for output\n"); ExitProgram(EXIT_FAILURE); } if (newterm(NULL, output, stdin) == 0) usage(); (void) cbreak(); /* read chars without wait for \n */ (void) noecho(); /* don't echo input */ update_modes(); curs_set(0); keypad(stdscr, TRUE); if ((hascolor = has_colors())) { start_color(); current = 1; } else { current = 0; } /* * Repeatedly cycle through all colors, initializing pairs as needed. * Provide for single-stepping, or page-at-a-time, as well as quitting. */ while (!done) { cchar_t temp; attr_t my_attrs; int my_pair; switch (getch()) { case HELP_KEY_1: popup_msg(stdscr, help); break; case 'p': /* step-by-page */ use_pages(); update_modes(); break; case 's': /* step-by-char */ use_single(); update_modes(); break; case ' ': single_mode = FALSE; update_modes(); break; case QUIT: case ESCAPE: case 'q': done = TRUE; continue; case 'c': clobber = !clobber; continue; case 'v': if (--video_mode < 0) video_mode = MAX_ATTR; continue; case 'V': if (video_mode > MAX_ATTR) video_mode = 0; continue; case 'w': use_wide = !use_wide; continue; case ERR: break; default: beep(); break; } if (hascolor) { my_attrs = next_attr(video_mode); if (clobber) { int fg, bg; our_content(current, &fg, &bg); my_pair = find_pair(fg, bg); if (my_pair > 0) { free_pair(my_pair); } my_pair = 0; } else { my_pair = (use_init ? next_color(current) : make_color(current)); } } else { my_attrs = next_attr(current); my_pair = 0; } if (my_pair < 0) break; wch[0] = use_wide ? 0xff03 : '#'; wch[1] = 0; setcchar(&temp, wch, my_attrs, (short) my_pair, NULL); /* * At the end of a page, move the cursor to the home position. */ if ((add_wch(&temp) == ERR) && paged_mode) { nodelay(stdscr, !single_mode); move(0, 0); } total_cells += 1 + (use_wide ? 1 : 0); ++current; } endwin(); fclose(output); printf("%.1f cells/second\n", (double) (total_cells) / (double) (now() - start)); ExitProgram(EXIT_SUCCESS); } #else int main(void) { printf("This program requires the ncurses alloc_pair function\n"); ExitProgram(EXIT_FAILURE); } #endif