diff --git a/nnn.c b/nnn.c index cd2fa1c3..00605769 100644 --- a/nnn.c +++ b/nnn.c @@ -343,6 +343,35 @@ all_dots(const char *ptr) return count; } +static void +initcurses(void) +{ + if (initscr() == NULL) { + char *term = getenv("TERM"); + + if (term != NULL) + fprintf(stderr, "error opening terminal: %s\n", term); + else + fprintf(stderr, "failed to initialize curses\n"); + exit(1); + } + cbreak(); + noecho(); + nonl(); + intrflush(stdscr, FALSE); + keypad(stdscr, TRUE); + curs_set(FALSE); /* Hide cursor */ + start_color(); + use_default_colors(); + timeout(1000); /* One second */ +} + +static void +exitcurses(void) +{ + endwin(); /* Restore terminal */ +} + /* * Spawns a child process. Behaviour can be controlled using flag: * Limited to 2 arguments to a program @@ -351,6 +380,7 @@ all_dots(const char *ptr) * - 0b10: do not wait in parent for child process e.g. DE file manager * - 0b100: suppress stdout and stderr * - 0b1000: restore default SIGINT handler + * - 0b10000000: exit curses mode */ static void spawn(char *file, char *arg1, char *arg2, char *dir, unsigned char flag) @@ -358,17 +388,20 @@ spawn(char *file, char *arg1, char *arg2, char *dir, unsigned char flag) pid_t pid; int status; + if (flag & 0b10000000) + exitcurses(); + pid = fork(); if (pid == 0) { if (dir != NULL) status = chdir(dir); /* Show a marker (to indicate nnn spawned shell) */ - if (flag & 0x01) + if (flag & 0b1) printf("\n +-++-++-+\n | n n n |\n +-++-++-+\n\n"); /* Suppress stdout and stderr */ - if (flag & 0x04) { + if (flag & 0b100) { int fd = open("/dev/null", O_WRONLY, 0200); dup2(fd, 1); @@ -376,16 +409,19 @@ spawn(char *file, char *arg1, char *arg2, char *dir, unsigned char flag) close(fd); } - if (flag & 0x08) + if (flag & 0b1000) signal(SIGINT, SIG_DFL); execlp(file, file, arg1, arg2, NULL); _exit(1); } else { - if (!(flag & 0x02)) + if (!(flag & 0b10)) /* Ignore interruptions */ while (waitpid(pid, &status, 0) == -1) DPRINTF_D(status); + DPRINTF_D(pid); + if (flag & 0b10000000) + initcurses(); } } @@ -557,35 +593,6 @@ entrycmp(const void *va, const void *vb) return xstricmp(pa->name, pb->name); } -static void -initcurses(void) -{ - if (initscr() == NULL) { - char *term = getenv("TERM"); - - if (term != NULL) - fprintf(stderr, "error opening terminal: %s\n", term); - else - fprintf(stderr, "failed to initialize curses\n"); - exit(1); - } - cbreak(); - noecho(); - nonl(); - intrflush(stdscr, FALSE); - keypad(stdscr, TRUE); - curs_set(FALSE); /* Hide cursor */ - start_color(); - use_default_colors(); - timeout(1000); /* One second */ -} - -static void -exitcurses(void) -{ - endwin(); /* Restore terminal */ -} - /* Messages show up at the bottom */ static void printmsg(char *msg) @@ -1304,8 +1311,10 @@ show_stats(char *fpath, char *fname, struct stat *sb) close(fd); + exitcurses(); get_output(NULL, 0, "cat", tmp, NULL, 1); unlink(tmp); + initcurses(); return 0; } @@ -1318,7 +1327,6 @@ show_mediainfo(char *fpath, char *arg) exitcurses(); get_output(NULL, 0, "mediainfo", fpath, arg, 1); initcurses(); - return 0; } @@ -1396,8 +1404,10 @@ show_help(void) dprintf(fd, "\n"); close(fd); + exitcurses(); get_output(NULL, 0, "cat", tmp, NULL, 1); unlink(tmp); + initcurses(); return 0; } @@ -1791,10 +1801,8 @@ nochange: if (editor) { mime = getmime(dents[cur].name); if (mime) { - exitcurses(); spawn(editor, newpath, NULL, - NULL, 0); - initcurses(); + NULL, 0b10000000); continue; } @@ -1807,16 +1815,14 @@ nochange: continue; if (strstr(g_buf, "text/") == g_buf) { - exitcurses(); spawn(editor, newpath, NULL, - NULL, 0); - initcurses(); + NULL, 0b10000000); continue; } } /* Invoke desktop opener as last resort */ - spawn(utils[0], newpath, NULL, NULL, 4); + spawn(utils[0], newpath, NULL, NULL, 0b100); continue; } default: @@ -1840,9 +1846,7 @@ nochange: printmsg("navigate-as-you-type off"); goto nochange; case SEL_SEARCH: - exitcurses(); - spawn(player, path, "search", NULL, 0); - initcurses(); + spawn(player, path, "search", NULL, 0b10000000); break; case SEL_NEXT: if (cur < ndents - 1) @@ -2166,10 +2170,8 @@ nochange: dentfree(dents); printerr(1, "lstat"); } else { - exitcurses(); r = show_stats(oldpath, dents[cur].name, &sb); - initcurses(); if (r < 0) { printmsg(strerror(errno)); goto nochange; @@ -2207,7 +2209,7 @@ nochange: goto nochange; } - spawn(desktop_manager, path, NULL, path, 0x06); + spawn(desktop_manager, path, NULL, path, 0b110); break; case SEL_FSIZE: sizeorder = !sizeorder; @@ -2254,36 +2256,28 @@ nochange: else snprintf(newpath, PATH_MAX, "%s/%s", path, dents[cur].name); - spawn(copier, newpath, NULL, NULL, 0); + spawn(copier, newpath, NULL, NULL, 0b0); printmsg(newpath); } else if (!copier) printmsg("NNN_COPIER is not set"); goto nochange; case SEL_HELP: - exitcurses(); show_help(); - initcurses(); break; case SEL_RUN: run = xgetenv(env, run); - exitcurses(); - spawn(run, NULL, NULL, path, 1); - initcurses(); + spawn(run, NULL, NULL, path, 0b10000001); /* Repopulate as directory content may have changed */ goto begin; case SEL_RUNARG: run = xgetenv(env, run); - exitcurses(); - spawn(run, dents[cur].name, NULL, path, 0); - initcurses(); + spawn(run, dents[cur].name, NULL, path, 0b10000000); break; } /* Screensaver */ if (idletimeout != 0 && idle == idletimeout) { idle = 0; - exitcurses(); - spawn(player, "", "screensaver", NULL, 8); - initcurses(); + spawn(player, "", "screensaver", NULL, 0b10001000); } } }