summaryrefslogtreecommitdiffstats
diff options
context:
space:
mode:
authorDave Davenport <qball@gmpclient.org>2017-05-31 11:05:45 +0200
committerDave Davenport <qball@gmpclient.org>2017-05-31 11:05:45 +0200
commit4d8784cf85a5108340a2b2a684e2bd1d9f77269d (patch)
tree29e6d513c317c4b2686cb9ea27d195d074861df2
parent8a6bdd827de065009fbc14b11dca23be61c77138 (diff)
Port fixes from icon-cleanup branch.
- Thread for fetching icons for drun. - Fixed placing of icons instead of adding place-holder token that can mis-render. - Give textbox TB_ICON flag.
-rw-r--r--include/widgets/textbox.h2
-rw-r--r--source/dialogs/drun.c115
-rw-r--r--source/dialogs/window.c14
-rw-r--r--source/view.c14
-rw-r--r--source/widgets/listview.c1
-rw-r--r--source/widgets/textbox.c42
6 files changed, 86 insertions, 102 deletions
diff --git a/include/widgets/textbox.h b/include/widgets/textbox.h
index 3a8b1583..48bc6c54 100644
--- a/include/widgets/textbox.h
+++ b/include/widgets/textbox.h
@@ -66,6 +66,7 @@ typedef struct
guint blink_timeout;
PangoFontMetrics *metrics;
+ int left_offset;
//
const char *theme_name;
} textbox;
@@ -85,6 +86,7 @@ typedef enum
TB_WRAP = 1 << 21,
TB_PASSWORD = 1 << 22,
TB_INDICATOR = 1 << 23,
+ TB_ICON = 1<<24,
} TextboxFlags;
/**
* Flags indicating current state of the textbox.
diff --git a/source/dialogs/drun.c b/source/dialogs/drun.c
index 907d5f2e..a10057e6 100644
--- a/source/dialogs/drun.c
+++ b/source/dialogs/drun.c
@@ -89,8 +89,9 @@ typedef struct
unsigned int cmd_list_length_actual;
unsigned int history_length;
// List of disabled entries.
- GHashTable *disabled_entries;
- unsigned int disabled_entries_length;
+ GHashTable *disabled_entries;
+ unsigned int disabled_entries_length;
+ GThread *thread;
} DRunModePrivateData;
struct RegexEvalArg
@@ -418,6 +419,47 @@ static void get_apps ( DRunModePrivateData *pd )
TICK_N ( "Get Desktop apps (system dirs)" );
}
+static void drun_icon_fetch ( gpointer data )
+{
+ // as long as dr->icon is updated atomicly.. (is a pointer write atomic?)
+ // this should be fine running in another thread.
+ GTimer *t = g_timer_new ();
+ DRunModePrivateData *pd = (DRunModePrivateData*)data;
+ for ( size_t i = 0; i < pd->cmd_list_length; i++ ) {
+ DRunModeEntry *dr = &( pd->entry_list[i] );
+ if ( dr->icon_name == NULL )
+ continue;
+ gchar *icon_path = nk_xdg_theme_get_icon ( pd->xdg_context, NULL, "Applications", dr->icon_name, 32, 1, TRUE );
+ if ( icon_path == NULL ) {
+ g_free(dr->icon_name);
+ dr->icon_name = NULL;
+ continue;
+ }
+ else
+ g_log ( G_LOG_DOMAIN, G_LOG_LEVEL_DEBUG, "Found Icon %s(%d): %s", dr->icon_name, 32, icon_path );
+
+ if ( g_str_has_suffix ( icon_path, ".png" ) )
+ dr->icon = cairo_image_surface_create_from_png(icon_path);
+ else if ( g_str_has_suffix ( icon_path, ".svg" ) )
+ dr->icon = cairo_image_surface_create_from_svg(icon_path, 32);
+ else {
+ g_log ( G_LOG_DOMAIN, G_LOG_LEVEL_DEBUG, "Icon type not yet supported: %s", icon_path );
+ char *r = dr->icon_name;
+ dr->icon_name = NULL;
+ g_free(r);
+ }
+ g_free(icon_path);
+ // if ( (i%100) == 99 )
+ {
+
+ rofi_view_reload();
+ }
+ }
+ rofi_view_reload();
+ g_log ( G_LOG_DOMAIN, G_LOG_LEVEL_DEBUG, "elapsed: %f\n" , g_timer_elapsed ( t, NULL));
+ g_timer_destroy ( t );
+}
+
static int drun_mode_init ( Mode *sw )
{
if ( mode_get_private_data ( sw ) == NULL ) {
@@ -426,6 +468,7 @@ static int drun_mode_init ( Mode *sw )
mode_set_private_data ( sw, (void *) pd );
pd->xdg_context = nk_xdg_theme_context_new ();
get_apps ( pd );
+ pd->thread = g_thread_new ( "icon-fetch-drun", drun_icon_fetch, pd );
}
return TRUE;
}
@@ -470,6 +513,10 @@ static ModeMode drun_mode_result ( Mode *sw, int mretv, char **input, unsigned i
}
else if ( ( mretv & MENU_ENTRY_DELETE ) && selected_line < rmpd->cmd_list_length ) {
if ( selected_line < rmpd->history_length ) {
+ if ( rmpd->thread ) {
+ g_thread_join ( rmpd->thread );
+ rmpd->thread = NULL;
+ }
delete_entry_history ( &( rmpd->entry_list[selected_line] ) );
drun_entry_clear ( &( rmpd->entry_list[selected_line] ) );
memmove ( &( rmpd->entry_list[selected_line] ), &rmpd->entry_list[selected_line + 1],
@@ -484,6 +531,10 @@ static void drun_mode_destroy ( Mode *sw )
{
DRunModePrivateData *rmpd = (DRunModePrivateData *) mode_get_private_data ( sw );
if ( rmpd != NULL ) {
+ if ( rmpd->thread ){
+ g_thread_join ( rmpd->thread );
+ rmpd->thread = NULL;
+ }
for ( size_t i = 0; i < rmpd->cmd_list_length; i++ ) {
drun_entry_clear ( &( rmpd->entry_list[i] ) );
}
@@ -508,13 +559,12 @@ static char *_get_display_value ( const Mode *sw, unsigned int selected_line, in
}
/* Free temp storage. */
DRunModeEntry *dr = &( pd->entry_list[selected_line] );
- /* We use '\t' as the icon placeholder for now */
if ( dr->generic_name == NULL ) {
- return g_markup_printf_escaped ( "<span alpha=\"1\">\uFFFC</span>%s", dr->name );
+ return g_markup_printf_escaped ( "%s", dr->name );
}
else {
- return g_markup_printf_escaped ( "<span alpha=\"1\">\uFFFC</span>%s <span weight='light' size='small'><i>(%s)</i></span>",
- dr->name, dr->generic_name );
+ return g_markup_printf_escaped ( "%s <span weight='light' size='small'><i>(%s)</i></span>", dr->name,
+ dr->generic_name );
}
}
@@ -522,58 +572,7 @@ static cairo_surface_t *_get_icon ( const Mode *sw, unsigned int selected_line,
{
DRunModePrivateData *pd = (DRunModePrivateData *) mode_get_private_data ( sw );
g_return_val_if_fail ( pd->entry_list != NULL, NULL );
- DRunModeEntry *dr = &( pd->entry_list[selected_line] );
- if ( dr->icon != NULL ) {
- return dr->icon;
- }
- if ( dr->icon_name == NULL ) {
- return NULL;
- }
-
- gchar *icon_path;
-
- if ( g_path_is_absolute ( dr->icon_name ) ) {
- icon_path = dr->icon_name;
- }
- else {
- const gchar *name = dr->icon_name;
- if ( g_str_has_suffix ( name, ".png" ) || g_str_has_suffix ( name, ".svg" ) || g_str_has_suffix ( name, ".xpm" ) ) {
- /* We truncate the extension if the .desktop file is not compliant
- * We cannot just strip at '.' because D-Bus-styled names are now common.
- */
- gchar *c = g_utf8_strrchr ( name, -1, '.' );
- g_assert_nonnull ( c );
- *c = '\0';
- c = g_utf8_strchr ( name, -1, G_DIR_SEPARATOR );
- if ( c != NULL ) {
- /* And just in case, we strip any path component too */
- *c = '\0';
- name = ++c;
- }
- }
- icon_path = nk_xdg_theme_get_icon ( pd->xdg_context, config.drun_icon_theme, "Applications", name, height, 1, TRUE );
- if ( icon_path != NULL ) {
- g_debug ( "Found Icon %s(%d): %s", name, height, icon_path );
- }
- g_free ( dr->icon_name );
- }
- dr->icon_name = NULL;
-
- if ( icon_path == NULL ) {
- return NULL;
- }
-
- if ( g_str_has_suffix ( icon_path, ".png" ) ) {
- dr->icon = cairo_image_surface_create_from_png ( icon_path );
- }
- else if ( g_str_has_suffix ( icon_path, ".svg" ) ) {
- dr->icon = cairo_image_surface_create_from_svg ( icon_path, height );
- }
- else {
- g_debug ( "Icon type not yet supported: %s", icon_path );
- }
-
- g_free ( icon_path );
+ DRunModeEntry *dr = &( pd->entry_list[selected_line] );
return dr->icon;
}
diff --git a/source/dialogs/window.c b/source/dialogs/window.c
index 80cf880c..d19e1c61 100644
--- a/source/dialogs/window.c
+++ b/source/dialogs/window.c
@@ -301,18 +301,18 @@ static client* window_client ( ModeModePrivateData *pd, xcb_window_t win )
c->title = window_get_text_prop ( c->window, xcb->ewmh._NET_WM_NAME );
if ( c->title == NULL ) {
- c->title = rofi_escape_markup ( window_get_text_prop ( c->window, XCB_ATOM_WM_NAME ) );
+ c->title = window_get_text_prop ( c->window, XCB_ATOM_WM_NAME );
}
pd->title_len = MAX ( c->title ? g_utf8_strlen ( c->title, -1 ) : 0, pd->title_len );
- c->role = rofi_escape_markup ( window_get_text_prop ( c->window, netatoms[WM_WINDOW_ROLE] ) );
+ c->role = window_get_text_prop ( c->window, netatoms[WM_WINDOW_ROLE] );
pd->role_len = MAX ( c->role ? g_utf8_strlen ( c->role, -1 ) : 0, pd->role_len );
cky = xcb_icccm_get_wm_class ( xcb->connection, c->window );
xcb_icccm_get_wm_class_reply_t wcr;
if ( xcb_icccm_get_wm_class_reply ( xcb->connection, cky, &wcr, NULL ) ) {
- c->class = rofi_escape_markup ( rofi_latin_to_utf8_strdup ( wcr.class_name, -1 ) );
- c->name = rofi_escape_markup ( rofi_latin_to_utf8_strdup ( wcr.instance_name, -1 ) );
+ c->class = rofi_latin_to_utf8_strdup ( wcr.class_name, -1 );
+ c->name = rofi_latin_to_utf8_strdup ( wcr.instance_name, -1 );
pd->name_len = MAX ( c->name ? g_utf8_strlen ( c->name, -1 ) : 0, pd->name_len );
xcb_icccm_get_wm_class_reply_wipe ( &wcr );
}
@@ -692,11 +692,6 @@ static gboolean helper_eval_cb ( const GMatchInfo *info, GString *str, gpointer
if ( match[1] == 'w' ) {
helper_eval_add_str ( str, d->c->wmdesktopstr, l, d->pd->wmdn_len );
}
- else if ( match[1] == 'i' ) {
- if ( config.show_icons ) {
- g_string_append ( str, "<span alpha=\"1\">\uFFFC</span>" );
- }
- }
else if ( match[1] == 'c' ) {
helper_eval_add_str ( str, d->c->class, l, d->pd->clf_len );
}
@@ -728,7 +723,6 @@ static char *_get_display_value ( const Mode *sw, unsigned int selected_line, in
if ( c == NULL ) {
return get_entry ? g_strdup ( "Window has fanished" ) : NULL;
}
- *state |= MARKUP;
if ( c->demands ) {
*state |= URGENT;
}
diff --git a/source/view.c b/source/view.c
index fc5a4fe6..6d2b7aea 100644
--- a/source/view.c
+++ b/source/view.c
@@ -906,19 +906,11 @@ static void update_callback ( textbox *t, unsigned int index, void *udata, TextB
else{
list = pango_attr_list_new ();
}
- int icon_height = textbox_get_font_height ( t );
+ int icon_height = textbox_get_font_height ( t );
- const gchar *visible_text = textbox_get_visible_text ( t );
- const gchar *icon_placeholder = g_utf8_strchr ( visible_text, -1, 0xFFFC );
- if ( icon_placeholder != NULL ) {
- cairo_surface_t *icon = mode_get_icon ( state->sw, state->line_map[index], icon_height );
- textbox_icon ( t, icon );
+ cairo_surface_t *icon = mode_get_icon ( state->sw, state->line_map[index], icon_height );
+ textbox_icon ( t, icon );
- textbox_set_icon_index ( t, g_utf8_pointer_to_offset ( visible_text, icon_placeholder ) );
- }
- else {
- textbox_set_icon_index ( t, -1 );
- }
if ( state->tokens && config.show_match ) {
ThemeHighlight th = { HL_BOLD | HL_UNDERLINE, { 0.0, 0.0, 0.0, 0.0 } };
th = rofi_theme_get_highlight ( WIDGET ( t ), "highlight", th );
diff --git a/source/widgets/listview.c b/source/widgets/listview.c
index 8d048bb6..5b82a8db 100644
--- a/source/widgets/listview.c
+++ b/source/widgets/listview.c
@@ -243,6 +243,7 @@ static void listview_recompute_elements ( listview *lv )
char *name = g_strjoin ( ".", lv->listview_name, "element", NULL );
for ( unsigned int i = lv->cur_elements; i < newne; i++ ) {
TextboxFlags flags = ( lv->multi_select ) ? TB_INDICATOR : 0;
+ flags |= (config.show_icons)? TB_ICON:0;
lv->boxes[i] = textbox_create_full ( WIDGET_TYPE_LISTVIEW_ELEMENT, name, flags, NORMAL, "" );
widget_set_trigger_action_handler ( WIDGET ( lv->boxes[i] ), listview_element_trigger_action, lv );
}
diff --git a/source/widgets/textbox.c b/source/widgets/textbox.c
index ee51367a..b2fcbded 100644
--- a/source/widgets/textbox.c
+++ b/source/widgets/textbox.c
@@ -143,6 +143,9 @@ textbox* textbox_create_full ( WidgetType type, const char *name, TextboxFlags f
tb->changed = FALSE;
tb->layout = pango_layout_new ( p_context );
+ if ( (tb->flags&TB_ICON) == TB_ICON) {
+ tb->left_offset = 1.2*textbox_get_estimated_char_height();
+ }
textbox_font ( tb, tbft );
tb->metrics = p_metrics;
@@ -186,7 +189,6 @@ textbox* textbox_create_full ( WidgetType type, const char *name, TextboxFlags f
tb->widget.trigger_action = textbox_editable_trigger_action;
}
- tb->icon_index = -1; //Don't draw the icon by default
// Enabled by default
tb->widget.enabled = rofi_theme_get_boolean ( WIDGET ( tb ), "enabled", TRUE );
@@ -269,12 +271,6 @@ void textbox_set_pango_attributes ( textbox *tb, PangoAttrList *list )
pango_layout_set_attributes ( tb->layout, list );
}
-void textbox_set_icon_index ( textbox *tb, int index )
-{
- tb->icon_index = index;
- widget_queue_redraw ( WIDGET ( tb ) );
-}
-
// set the default text to display
void textbox_text ( textbox *tb, const char *text )
{
@@ -315,10 +311,9 @@ void textbox_icon ( textbox *tb, cairo_surface_t *icon )
// within the parent handled auto width/height modes
void textbox_moveresize ( textbox *tb, int x, int y, int w, int h )
{
- unsigned int offset = ( tb->flags & TB_INDICATOR ) ? DOT_OFFSET : 0;
+ unsigned int offset = tb->left_offset + ( tb->flags & TB_INDICATOR ) ? DOT_OFFSET : 0;
if ( tb->flags & TB_AUTOWIDTH ) {
pango_layout_set_width ( tb->layout, -1 );
- unsigned int offset = ( tb->flags & TB_INDICATOR ) ? DOT_OFFSET : 0;
w = textbox_get_font_width ( tb ) + widget_padding_get_padding_width ( WIDGET ( tb ) ) + offset;
}
else {
@@ -371,7 +366,7 @@ static void textbox_free ( widget *wid )
static void textbox_draw ( widget *wid, cairo_t *draw )
{
textbox *tb = (textbox *) wid;
- unsigned int offset = ( tb->flags & TB_INDICATOR ) ? DOT_OFFSET : 0;
+ unsigned int offset = tb->left_offset + (( tb->flags & TB_INDICATOR ) ? DOT_OFFSET : 0);
if ( tb->changed ) {
__textbox_update_pango_text ( tb );
@@ -383,21 +378,22 @@ static void textbox_draw ( widget *wid, cairo_t *draw )
int y = top + ( pango_font_metrics_get_ascent ( tb->metrics ) - pango_layout_get_baseline ( tb->layout ) ) / PANGO_SCALE;
// draw Icon
- int iconheight = textbox_get_font_height ( tb );
- int translatex = ( textbox_get_estimated_char_height () * tb->icon_index / 2 );
- if ( tb->icon != NULL && tb->icon_index != -1 ) {
- cairo_save ( draw );
+ if ( (tb->flags|TB_ICON) == TB_ICON && tb->icon != NULL ) {
+ int iconheight = textbox_get_font_height ( tb );
+ int translatex = 0;
+ cairo_save(draw);
/*int iconw = cairo_image_surface_get_width (tb->icon);*/
- int iconh = cairo_image_surface_get_height ( tb->icon );
- double scale = (double) iconheight / iconh;
+ int iconh = cairo_image_surface_get_height (tb->icon);
+ double scale = (double)iconheight / iconh;
- cairo_translate ( draw, translatex, 0 );
- cairo_scale ( draw, scale, scale );
- cairo_set_source_surface ( draw, tb->icon, x, y );
- cairo_paint ( draw );
- cairo_restore ( draw );
+ cairo_translate(draw, translatex, 0);
+ cairo_scale(draw, scale, scale);
+ cairo_set_source_surface(draw, tb->icon, x, y);
+ cairo_paint(draw);
+ cairo_restore(draw);
}
+ x+=offset;
if ( tb->flags & TB_RIGHT ) {
int line_width = 0;
@@ -438,7 +434,7 @@ static void textbox_draw ( widget *wid, cairo_t *draw )
pango_cairo_show_layout ( draw, tb->layout );
if ( ( tb->flags & TB_INDICATOR ) == TB_INDICATOR && ( tb->tbft & ( SELECTED ) ) ) {
- cairo_arc ( draw, DOT_OFFSET / 2.0, tb->widget.h / 2.0, 2.0, 0, 2.0 * G_PI );
+ cairo_arc ( draw, tb->left_offset + DOT_OFFSET / 2.0, tb->widget.h / 2.0, 2.0, 0, 2.0 * M_PI );
cairo_fill ( draw );
}
}
@@ -852,7 +848,7 @@ int textbox_get_estimated_height ( const textbox *tb, int eh )
int textbox_get_desired_width ( widget *wid )
{
textbox *tb = (textbox *) wid;
- unsigned int offset = ( tb->flags & TB_INDICATOR ) ? DOT_OFFSET : 0;
+ unsigned int offset = tb->left_offset + ( tb->flags & TB_INDICATOR ) ? DOT_OFFSET : 0;
if ( tb->flags & TB_AUTOWIDTH ) {
return textbox_get_font_width ( tb ) + widget_padding_get_padding_width ( wid ) + offset;
}