From 1342b733af6a8de481ac35a33cb352c21efcd0b5 Mon Sep 17 00:00:00 2001 From: Dave Davenport Date: Sun, 24 May 2020 19:09:06 +0200 Subject: [PATCH] [Script] Add 'info' row option, that gets passed to ROFI_INFO environment. --- Examples/test_script_env.sh | 8 +++++++- doc/rofi-script.5 | 18 ++++++++++++++++++ doc/rofi-script.5.markdown | 11 +++++++++++ include/dialogs/dmenuscriptshared.h | 4 ++++ source/dialogs/dmenu.c | 2 ++ source/dialogs/script.c | 28 ++++++++++++++++++++++------ source/widgets/listview.c | 1 - 7 files changed, 64 insertions(+), 8 deletions(-) diff --git a/Examples/test_script_env.sh b/Examples/test_script_env.sh index 7753a845..9a8f52dd 100755 --- a/Examples/test_script_env.sh +++ b/Examples/test_script_env.sh @@ -5,5 +5,11 @@ then echo "run this script in rofi". exit fi + echo -en "\x00no-custom\x1ftrue\n" -echo "${ROFI_RETV}" +echo -en "${ROFI_RETV}\x00icon\x1ffirefox\x1finfo\x1ftest\n" + +if [ -n "${ROFI_INFO}" ] +then + echo "my info: ${ROFI_INFO} " +fi diff --git a/doc/rofi-script.5 b/doc/rofi-script.5 index e5fa1b96..93318765 100644 --- a/doc/rofi-script.5 +++ b/doc/rofi-script.5 @@ -73,6 +73,10 @@ An integer number with the current state: .IP \(bu 2 \fB10\-28\fP: Custom keybinding 1\-19 +.SS \fB\fCROFI\_INFO\fR +.PP +Environment get set when selected entry get set with the property value of the 'info' row option, if set. + .SH Passing mode options .PP Extra options, like setting the prompt, can be set by the script. @@ -132,6 +136,20 @@ The following options are supported: \fBmeta\fP: Specify invisible search terms. .IP \(bu 2 \fBnonselectable\fP: If true the row cannot activated. +.IP \(bu 2 +\fBinfo\fP: Info that, on selection, gets placed in the \fB\fCROFI\_INFO\fR environment variable. This entry does not get searched. + +.PP +multiple entries can be passed using the \fB\fC\\x1f\fR separator. + +.PP +.RS + +.nf + echo \-en "aap\\0icon\\x1ffolder\\x1finfo\\x1ftest\\n" + +.fi +.RE .SH SEE ALSO .PP diff --git a/doc/rofi-script.5.markdown b/doc/rofi-script.5.markdown index 7f63b439..f9f85800 100644 --- a/doc/rofi-script.5.markdown +++ b/doc/rofi-script.5.markdown @@ -59,6 +59,10 @@ An integer number with the current state: * **2**: Selected a custom entry. * **10-28**: Custom keybinding 1-19 +### `ROFI_INFO` + +Environment get set when selected entry get set with the property value of the 'info' row option, if set. + ## Passing mode options Extra options, like setting the prompt, can be set by the script. @@ -96,6 +100,13 @@ The following options are supported: * **icon**: Set the icon for that row. * **meta**: Specify invisible search terms. * **nonselectable**: If true the row cannot activated. + * **info**: Info that, on selection, gets placed in the `ROFI_INFO` environment variable. This entry does not get searched. + +multiple entries can be passed using the `\x1f` separator. + +```bash + echo -en "aap\0icon\x1ffolder\x1finfo\x1ftest\n" +``` diff --git a/include/dialogs/dmenuscriptshared.h b/include/dialogs/dmenuscriptshared.h index a7f1f47a..951d2b55 100644 --- a/include/dialogs/dmenuscriptshared.h +++ b/include/dialogs/dmenuscriptshared.h @@ -11,6 +11,10 @@ typedef struct uint32_t icon_fetch_uid; /** Hidden meta keywords. */ char *meta; + + /** info */ + char *info; + /** non-selectable */ gboolean nonselectable; } DmenuScriptEntry; diff --git a/source/dialogs/dmenu.c b/source/dialogs/dmenu.c index 5e9af2d4..d94211c9 100644 --- a/source/dialogs/dmenu.c +++ b/source/dialogs/dmenu.c @@ -122,6 +122,7 @@ static void read_add ( DmenuModePrivateData * pd, char *data, gsize len ) pd->cmd_list[pd->cmd_list_length].icon_fetch_uid = 0; pd->cmd_list[pd->cmd_list_length].icon_name = NULL; pd->cmd_list[pd->cmd_list_length].meta = NULL; + pd->cmd_list[pd->cmd_list_length].info = NULL; char *end = strchr ( data, '\0' ); if ( end != NULL ) { data_len = end - data; @@ -314,6 +315,7 @@ static void dmenu_mode_free ( Mode *sw ) g_free ( pd->cmd_list[i].entry ); g_free ( pd->cmd_list[i].icon_name ); g_free ( pd->cmd_list[i].meta ); + g_free ( pd->cmd_list[i].info ); } } g_free ( pd->cmd_list ); diff --git a/source/dialogs/script.c b/source/dialogs/script.c index d008996e..b217a851 100644 --- a/source/dialogs/script.c +++ b/source/dialogs/script.c @@ -79,12 +79,18 @@ typedef struct void dmenuscript_parse_entry_extras ( G_GNUC_UNUSED Mode *sw, DmenuScriptEntry *entry, char *buffer, size_t length ) { size_t length_key = 0; //strlen ( line ); + size_t end_value = 0; while ( length_key < length && buffer[length_key] != '\x1f' ) { length_key++; } + end_value = length_key+1; + while ( end_value < length && buffer[end_value] != '\x1f' ) { + end_value++; + } // Should be not last character in buffer. if ( (length_key+1) < (length) ) { buffer[length_key] = '\0'; + if ( end_value < length_key) buffer[end_value] = '\0'; char *value = buffer + length_key + 1; if ( strcasecmp ( buffer, "icon" ) == 0 ) { entry->icon_name = g_strdup ( value ); @@ -92,10 +98,16 @@ void dmenuscript_parse_entry_extras ( G_GNUC_UNUSED Mode *sw, DmenuScriptEntry * else if ( strcasecmp ( buffer, "meta" ) == 0 ) { entry->meta = g_strdup ( value ); } + else if ( strcasecmp ( buffer, "info" ) == 0 ) { + entry->info = g_strdup ( value ); + } else if ( strcasecmp ( buffer, "nonselectable" ) == 0 ) { entry->nonselectable = strcasecmp ( value, "true" ) == 0; } } + if ( end_value < length ) { + dmenuscript_parse_entry_extras ( NULL, entry, &buffer[end_value+1], length-end_value); + } } /** @@ -139,7 +151,7 @@ static void parse_header_entry ( Mode *sw, char *line, ssize_t length ) } } -static DmenuScriptEntry *execute_executor ( Mode *sw, char *arg, unsigned int *length, int value ) +static DmenuScriptEntry *execute_executor ( Mode *sw, char *arg, unsigned int *length, int value, DmenuScriptEntry *entry ) { ScriptModePrivateData *pd = (ScriptModePrivateData *) sw->private_data; int fd = -1; @@ -161,6 +173,10 @@ static DmenuScriptEntry *execute_executor ( Mode *sw, char *arg, unsigned int *l env = g_environ_setenv ( env, "ROFI_OUTSIDE", str_value, TRUE); g_free ( str_value ); + if ( entry && entry->info ) { + env = g_environ_setenv ( env, "ROFI_INFO", entry->info, TRUE); + } + if ( g_shell_parse_argv ( sw->ed, &argc, &argv, &error ) ) { argv = g_realloc ( argv, ( argc + 2 ) * sizeof ( char* ) ); @@ -239,7 +255,7 @@ static int script_mode_init ( Mode *sw ) ScriptModePrivateData *pd = g_malloc0 ( sizeof ( *pd ) ); pd->delim = '\n'; sw->private_data = (void *) pd; - pd->cmd_list = execute_executor ( sw, NULL, &( pd->cmd_list_length ), 0 ); + pd->cmd_list = execute_executor ( sw, NULL, &( pd->cmd_list_length ), 0, NULL ); } return TRUE; } @@ -278,10 +294,10 @@ static ModeMode script_mode_result ( Mode *sw, int mretv, char **input, unsigned //retv = 1+( mretv & MENU_LOWER_MASK ); script_mode_reset_highlight ( sw ); if ( selected_line != UINT32_MAX ) { - new_list = execute_executor ( sw, rmpd->cmd_list[selected_line].entry, &new_length,10+( mretv & MENU_LOWER_MASK ) ); + new_list = execute_executor ( sw, rmpd->cmd_list[selected_line].entry, &new_length,10+( mretv & MENU_LOWER_MASK ), &(rmpd->cmd_list[selected_line]) ); } else { if ( rmpd->no_custom == FALSE ) { - new_list = execute_executor ( sw, *input, &new_length,10+( mretv & MENU_LOWER_MASK ) ); + new_list = execute_executor ( sw, *input, &new_length,10+( mretv & MENU_LOWER_MASK ), NULL ); } else { return RELOAD_DIALOG; } @@ -292,12 +308,12 @@ static ModeMode script_mode_result ( Mode *sw, int mretv, char **input, unsigned return RELOAD_DIALOG; } script_mode_reset_highlight ( sw ); - new_list = execute_executor ( sw, rmpd->cmd_list[selected_line].entry, &new_length, 1 ); + new_list = execute_executor ( sw, rmpd->cmd_list[selected_line].entry, &new_length, 1, NULL ); } else if ( ( mretv & MENU_CUSTOM_INPUT ) && *input != NULL && *input[0] != '\0' ) { if ( rmpd->no_custom == FALSE ) { script_mode_reset_highlight ( sw ); - new_list = execute_executor ( sw, *input, &new_length, 2 ); + new_list = execute_executor ( sw, *input, &new_length, 2 , &(rmpd->cmd_list[selected_line])); } else { return RELOAD_DIALOG; } diff --git a/source/widgets/listview.c b/source/widgets/listview.c index 8df1cf9a..25409f7a 100644 --- a/source/widgets/listview.c +++ b/source/widgets/listview.c @@ -194,7 +194,6 @@ static void listview_add_widget ( listview *lv, _listview_row *row, widget *wid, static void listview_create_row ( listview *lv, _listview_row *row ) { - TextboxFlags flags = ( lv->multi_select ) ? TB_INDICATOR : 0; row->box = box_create ( WIDGET ( lv ), "element", ROFI_ORIENTATION_HORIZONTAL ); widget_set_type ( WIDGET ( row->box ), WIDGET_TYPE_LISTVIEW_ELEMENT ); GList *list = rofi_theme_get_list ( WIDGET ( row->box ), "children", "element-icon,element-text" );