/*
* rofi
*
* MIT/X11 License
* Copyright © 2013-2019 Qball Cow <qball@gmpclient.org>
*
* 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, 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 AUTHORS OR 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.
*
*/
/** The log domain of this dialog. */
#define G_LOG_DOMAIN "Dialogs.DRun"
#include <config.h>
#ifdef ENABLE_DRUN
#include <stdlib.h>
#include <stdio.h>
#include <limits.h>
#include <unistd.h>
#include <limits.h>
#include <signal.h>
#include <sys/types.h>
#include <sys/stat.h>
#include <dirent.h>
#include <strings.h>
#include <string.h>
#include <errno.h>
#include "rofi.h"
#include "settings.h"
#include "helper.h"
#include "timings.h"
#include "widgets/textbox.h"
#include "history.h"
#include "dialogs/drun.h"
#include "xcb.h"
#include "rofi-icon-fetcher.h"
#define DRUN_CACHE_FILE "rofi3.druncache"
char *DRUN_GROUP_NAME = "Desktop Entry";
typedef struct _DRunModePrivateData DRunModePrivateData;
/**
* Store extra information about the entry.
* Currently the executable and if it should run in terminal.
*/
typedef struct
{
thread_state st;
DRunModePrivateData *pd;
/* category */
char *action;
/* Root */
char *root;
/* Path to desktop file */
char *path;
/* Application id (.desktop filename) */
char *app_id;
/* Desktop id */
char *desktop_id;
/* Icon stuff */
char *icon_name;
/* Icon size is used to indicate what size is requested by the gui.
* secondary it indicates if the request for a lookup has been issued (0 not issued )
*/
int icon_size;
/* Surface holding the icon. */
cairo_surface_t *icon;
/* Executable */
char *exec;
/* Name of the Entry */
char *name;
/* Generic Name */
char *generic_name;
/* Categories */
char **categories;
/* Keywords */
char **keywords;
/* Comments */
char *comment;
GKeyFile *key_file;
gint sort_index;
uint32_t icon_fetch_uid;
} DRunModeEntry;
typedef struct
{
const char *entry_field_name;
gboolean enabled;
} DRunEntryField;
typedef enum
{
DRUN_MATCH_FIELD_NAME,
DRUN_MATCH_FIELD_GENERIC,
DRUN_MATCH_FIELD_EXEC,
DRUN_MATCH_FIELD_CATEGORIES,
DRUN_MATCH_FIELD_KEYWORDS,
DRUN_MATCH_FIELD_COMMENT,
DRUN_MATCH_NUM_FIELDS,
} DRunMatchingFields;
static DRunEntryField matching_entry_fields[DRUN_MATCH_NUM_FIELDS] = {
{ .entry_field_name = "name", .enabled = TRUE, },
{ .entry_field_name = "generic", .enabled = TRUE, },
{ .entry_field_name = "exec", .enabled = TRUE, },
{ .entry_field_name = "categories", .enabled = TRUE, },
{ .entry_field_name = "keywords", .enabled = TRUE, },
{ .entry_field_name = "comment", .enabled = FALSE, }
};
struct _DRunModePrivateData
{
DRunModeEntry *entry_list;
unsigned int cmd_list_length;
unsigned int cmd_list_length_actual;
// List of disabled entries.
GHashTable *disabled_entries;
unsigned int disabled_entries_length;
unsigned int expected_line_height;
char **show_categories;
// Theme
const gchar *icon_theme;
// DE
gchar **current_desktop_list;
};
struct RegexEvalArg
{
DRunModeEntry *e;
gboolean success;
};
static gboolean drun_helper_eval_cb ( const GMatchInfo *info, GString *res, gpointer data )
{
// TODO quoting is not right? Find description not very clear, need to check.
struct RegexEvalArg *e = (struct RegexEvalArg *) data;
gchar *match;
// Get the match
match = g_match_info_fetch ( info, 0 );
if ( match != NULL ) {
switch ( match[1] )
{
// Unsupported
case 'f':
case 'F':
case 'u':
case 'U':
case 'i':
// Deprecated
case 'd':
case 'D':
case 'n':
case 'N':
case 'v':
case 'm':
break;