From fe423ed2794273445ad51332d08b19155bcbc3e8 Mon Sep 17 00:00:00 2001 From: verdant Date: Tue, 28 Jul 2026 14:46:43 +0800 Subject: Implement open with editor Fork a child process to run the text editor. If the "EDITOR" envrionment variable is not set, fallback to "vi". --- fm.c | 45 +++++++++++++++++++++++++++++++++++++++++++++ 1 file changed, 45 insertions(+) (limited to 'fm.c') diff --git a/fm.c b/fm.c index 17d0b7f..1d1302c 100644 --- a/fm.c +++ b/fm.c @@ -6,6 +6,7 @@ #include "wm.h" #include #include +#include #include #include #include @@ -14,9 +15,12 @@ #include #include #include +#include #include static magic_t g_magic_ctx = NULL; +static char *const utils[] = {"vi", "xdg-open"}; +static char *const envs[] = {"SHELL", "EDITOR", "SF"}; bool need_redraw = true; /* Function forward declarations */ @@ -24,6 +28,9 @@ static fm_info *fm_w_init(terminal *term); static void fm_file_list_init(file_list *l, int cap); static void fm_file_items_realloc(file_list *l); static char *detect_file_type(const char *filepath); +static void fm_getenv(void); +static char *xgetenv(const char *const name, char *fallback); +int open_with_editor(char **argv); bool fm_preview_file(window *w, const char *path); /* Functions */ @@ -119,6 +126,7 @@ static void fm_file_list_init(file_list *l, int cap) l->items = xmalloc(sizeof(file_item) * cap); l->items->is_dir = 0; memset(l->items, 0, l->cap * sizeof(file_item)); + fm_getenv(); } fm_info *fm_init(terminal *t) @@ -334,3 +342,40 @@ void magic_cleanup(void) if (g_magic_ctx) magic_close(g_magic_ctx); } +static char *xgetenv(const char *const name, char *fallback) +{ + char *value = getenv(name); + + return value && value[0] ? value : fallback; +} + +static void fm_getenv(void) +{ + enveditor = xgetenv(envs[ENV_EDITOR], utils[UTIL_VI]); +} + +int open_with_editor(char **argv) +{ + pid_t pid; + def_prog_mode(); + endwin(); + + if (!argv[0] || *argv[0] == '\0') { + argv[0] = utils[UTIL_VI]; + } + + if ((pid = fork()) < 0) { + log_write(LOG_ERR, "fork error"); + return -1; + } else if (pid == 0) { + if (execvp(argv[0], argv) < 0) { + log_write(LOG_ERR, "execvp error"); + return -1; + } + } else { + wait(NULL); + need_redraw = true; + } + + return 0; +} -- cgit v1.2.3