2 * icons.[ch] written by Paolo Bacchilega, who writes:
3 * "There is no problem for me, you can license my code under whatever licence you wish :)"
5 * $Id: icons.c 11284 2010-10-01 20:22:51Z charles $
8 #include <string.h> /* strcmp */
14 #if GTK_CHECK_VERSION( 2, 12, 0 )
23 #define VOID_PIXBUF_KEY "void-pixbuf"
27 get_static_string( const char *s
)
29 static GStringChunk
* static_strings
= NULL
;
34 if( static_strings
== NULL
)
35 static_strings
= g_string_chunk_new( 1024 );
37 return g_string_chunk_insert_const( static_strings
, s
);
43 GtkIconTheme
* icon_theme
;
49 static IconCache
*icon_cache
[7] = { NULL
, NULL
, NULL
, NULL
, NULL
, NULL
, NULL
};
53 create_void_pixbuf (int width
,
58 p
= gdk_pixbuf_new( GDK_COLORSPACE_RGB
,
63 gdk_pixbuf_fill( p
, 0xFFFFFF00 );
70 get_size_in_pixels( GtkWidget
* widget
,
71 GtkIconSize icon_size
)
75 gtk_icon_size_lookup_for_settings( gtk_widget_get_settings( widget
),
79 return MAX( width
, height
);
84 icon_cache_new (GtkWidget
* for_widget
, int icon_size
)
86 IconCache
* icon_cache
;
88 g_return_val_if_fail( for_widget
!= NULL
, NULL
);
90 icon_cache
= g_new0( IconCache
, 1 );
91 icon_cache
->icon_theme
= gtk_icon_theme_get_for_screen( gtk_widget_get_screen( for_widget
));
92 icon_cache
->icon_size
= get_size_in_pixels( for_widget
, icon_size
);
93 icon_cache
->cache
= g_hash_table_new_full (g_str_hash
, g_str_equal
, NULL
, g_object_unref
);
95 g_hash_table_insert( icon_cache
->cache
, (void*)VOID_PIXBUF_KEY
, create_void_pixbuf( icon_cache
->icon_size
, icon_cache
->icon_size
));
102 _icon_cache_get_icon_key( GIcon
* icon
)
104 const char * key
= NULL
;
106 if ( G_IS_THEMED_ICON( icon
)) {
110 g_object_get( icon
, "names", &icon_names
, NULL
);
111 name
= g_strjoinv( ",", icon_names
);
113 key
= get_static_string( name
);
116 g_strfreev( icon_names
);
118 else if ( G_IS_FILE_ICON( icon
)) {
122 file
= g_file_icon_get_file( G_FILE_ICON( icon
));
123 filename
= g_file_get_path( file
);
125 key
= get_static_string( filename
);
128 g_object_unref( file
);
136 get_themed_icon_pixbuf( GThemedIcon
* icon
,
138 GtkIconTheme
* icon_theme
)
140 char ** icon_names
= NULL
;
141 GtkIconInfo
* icon_info
;
143 GError
* error
= NULL
;
145 g_object_get( icon
, "names", &icon_names
, NULL
);
147 icon_info
= gtk_icon_theme_choose_icon( icon_theme
, (const char **)icon_names
, size
, 0 );
148 if ( icon_info
== NULL
)
149 icon_info
= gtk_icon_theme_lookup_icon( icon_theme
, "text-x-generic", size
, GTK_ICON_LOOKUP_USE_BUILTIN
);
151 pixbuf
= gtk_icon_info_load_icon( icon_info
, &error
);
152 if ( pixbuf
== NULL
) {
153 if( error
&& error
->message
)
154 g_warning( "could not load icon pixbuf: %s\n", error
->message
);
155 g_clear_error( &error
);
158 gtk_icon_info_free( icon_info
);
159 g_strfreev( icon_names
);
166 get_file_icon_pixbuf( GFileIcon
* icon
, int size
)
172 file
= g_file_icon_get_file( icon
);
173 filename
= g_file_get_path( file
);
174 pixbuf
= gdk_pixbuf_new_from_file_at_size( filename
, size
, -1, NULL
);
176 g_object_unref( file
);
183 _get_icon_pixbuf( GIcon
* icon
, int size
, GtkIconTheme
* theme
)
187 if ( G_IS_THEMED_ICON (icon
) )
188 return get_themed_icon_pixbuf( G_THEMED_ICON( icon
), size
, theme
);
189 if ( G_IS_FILE_ICON (icon
) )
190 return get_file_icon_pixbuf( G_FILE_ICON( icon
), size
);
196 icon_cache_get_mime_type_icon( IconCache
* icon_cache
, const char * mime_type
)
199 const char * key
= NULL
;
202 icon
= g_content_type_get_icon( mime_type
);
203 key
= _icon_cache_get_icon_key( icon
);
206 key
= VOID_PIXBUF_KEY
;
208 pixbuf
= g_hash_table_lookup( icon_cache
->cache
, key
);
209 if (pixbuf
!= NULL
) {
210 g_object_ref( pixbuf
);
211 g_object_unref( G_OBJECT( icon
) );
215 pixbuf
= _get_icon_pixbuf( icon
, icon_cache
->icon_size
, icon_cache
->icon_theme
);
217 g_hash_table_insert( icon_cache
->cache
, (gpointer
) key
, g_object_ref( pixbuf
) );
219 g_object_unref( G_OBJECT( icon
) );
224 #else /* USE_GIO_ICONS */
227 icon_cache_get_mime_type_icon( IconCache
* icon_cache
, const char * mime_type
)
230 const char * stock_name
;
232 if( !strcmp( mime_type
, UNKNOWN_MIME_TYPE
) )
233 stock_name
= GTK_STOCK_MISSING_IMAGE
;
234 else if( !strcmp( mime_type
, DIRECTORY_MIME_TYPE
) )
235 stock_name
= GTK_STOCK_DIRECTORY
;
237 stock_name
= GTK_STOCK_FILE
;
239 pixbuf
= g_hash_table_lookup( icon_cache
->cache
, stock_name
);
243 g_object_ref( pixbuf
);
247 pixbuf
= gtk_icon_theme_load_icon( icon_cache
->icon_theme
,
249 icon_cache
->icon_size
,
251 g_hash_table_insert( icon_cache
->cache
, (gpointer
) stock_name
, g_object_ref( pixbuf
));
259 get_mime_type_icon( const char * mime_type
,
260 GtkIconSize icon_size
,
261 GtkWidget
* for_widget
)
265 switch ( icon_size
) {
266 case GTK_ICON_SIZE_MENU
: n
= 1; break;
267 case GTK_ICON_SIZE_SMALL_TOOLBAR
: n
= 2; break;
268 case GTK_ICON_SIZE_LARGE_TOOLBAR
: n
= 3; break;
269 case GTK_ICON_SIZE_BUTTON
: n
= 4; break;
270 case GTK_ICON_SIZE_DND
: n
= 5; break;
271 case GTK_ICON_SIZE_DIALOG
: n
= 6; break;
272 default /*GTK_ICON_SIZE_INVALID*/: n
= 0; break;
275 if( icon_cache
[n
] == NULL
)
276 icon_cache
[n
] = icon_cache_new( for_widget
, icon_size
);
278 return icon_cache_get_mime_type_icon( icon_cache
[n
], mime_type
);
283 get_mime_type_from_filename( const char * file G_GNUC_UNUSED
)
286 char * tmp
= g_content_type_guess( file
, NULL
, 0, NULL
);
287 const char * ret
= get_static_string( tmp
);