summaryrefslogtreecommitdiff
diff options
context:
space:
mode:
authorrbuj <[email protected]>2020-07-25 14:15:59 +0200
committerraveit65 <[email protected]>2020-08-27 12:33:35 +0200
commit58e338e80ac0e611626f5b2e62a2f32a4059025a (patch)
treea0a6b2ab1bda22865e68e0e46c800e56fd937ea9
parent706246d2dcb4bc3b41cf3a45c13266ed42be63b9 (diff)
downloadmate-system-monitor-58e338e80ac0e611626f5b2e62a2f32a4059025a.tar.bz2
mate-system-monitor-58e338e80ac0e611626f5b2e62a2f32a4059025a.tar.xz
pretty-table: prefer GIO to get application icons
-rw-r--r--src/iconthemewrapper.cpp28
-rw-r--r--src/iconthemewrapper.h2
-rw-r--r--src/prettytable.cpp59
-rw-r--r--src/prettytable.h11
4 files changed, 98 insertions, 2 deletions
diff --git a/src/iconthemewrapper.cpp b/src/iconthemewrapper.cpp
index e44bdcd..f5ab4ef 100644
--- a/src/iconthemewrapper.cpp
+++ b/src/iconthemewrapper.cpp
@@ -27,3 +27,31 @@ procman::IconThemeWrapper::load_icon(const Glib::ustring& icon_name, int size) c
}
}
+Glib::RefPtr<Gdk::Pixbuf>
+procman::IconThemeWrapper::load_gicon(const Glib::RefPtr<Gio::Icon>& gicon,
+ int size, Gtk::IconLookupFlags flags) const
+{
+ Gtk::IconInfo icon_info;
+ gint scale = gdk_window_get_scale_factor (gdk_get_default_root_window ());
+ icon_info = Gtk::IconTheme::get_default()->lookup_icon(gicon, size, scale, flags);
+
+ if (!icon_info) {
+ return Glib::RefPtr<Gdk::Pixbuf>();
+ }
+
+ try
+ {
+ return icon_info.load_icon();
+ }
+ catch (Gtk::IconThemeError &error)
+ {
+ if (error.code() != Gtk::IconThemeError::ICON_THEME_NOT_FOUND)
+ g_error("Cannot load gicon from theme: %s", error.what().c_str());
+ return Glib::RefPtr<Gdk::Pixbuf>();
+ }
+ catch (Gio::Error &error)
+ {
+ g_debug("Could not load gicon: %s", error.what().c_str());
+ return Glib::RefPtr<Gdk::Pixbuf>();
+ }
+}
diff --git a/src/iconthemewrapper.h b/src/iconthemewrapper.h
index 3a8bde5..81222b9 100644
--- a/src/iconthemewrapper.h
+++ b/src/iconthemewrapper.h
@@ -14,6 +14,8 @@ namespace procman
// returns 0 instead of raising an exception
Glib::RefPtr<Gdk::Pixbuf>
load_icon(const Glib::ustring& icon_name, int size) const;
+ Glib::RefPtr<Gdk::Pixbuf>
+ load_gicon(const Glib::RefPtr<Gio::Icon>& gicon, int size, Gtk::IconLookupFlags flags) const;
const IconThemeWrapper* operator->() const
{ return this; }
diff --git a/src/prettytable.cpp b/src/prettytable.cpp
index 7b8bed6..cbc5f0d 100644
--- a/src/prettytable.cpp
+++ b/src/prettytable.cpp
@@ -7,6 +7,10 @@
#include <string.h>
#include <gdk-pixbuf/gdk-pixbuf.h>
#include <glibtop/procstate.h>
+#include <giomm/error.h>
+#include <giomm/file.h>
+#include <glibmm/miscutils.h>
+#include <iostream>
#include <vector>
@@ -29,6 +33,20 @@ PrettyTable::PrettyTable()
G_CALLBACK(PrettyTable::on_application_opened), this);
g_signal_connect(G_OBJECT(screen), "application_closed",
G_CALLBACK(PrettyTable::on_application_closed), this);
+
+ // init GIO apps cache
+ std::vector<std::string> dirs = Glib::get_system_data_dirs();
+ for (std::vector<std::string>::iterator it = dirs.begin(); it != dirs.end(); ++it) {
+ std::string path = (*it).append("/applications");
+ Glib::RefPtr<Gio::File> file = Gio::File::create_for_path(path);
+ Glib::RefPtr<Gio::FileMonitor> monitor = file->monitor_directory();
+ monitor->set_rate_limit(1000); // 1 second
+
+ monitor->signal_changed().connect(sigc::mem_fun(this, &PrettyTable::file_monitor_event));
+ monitors[path] = monitor;
+ }
+
+ this->init_gio_app_cache();
}
@@ -87,8 +105,6 @@ PrettyTable::register_application(pid_t pid, Glib::RefPtr<Gdk::Pixbuf> icon)
}
}
-
-
void
PrettyTable::on_application_closed(WnckScreen* screen, WnckApplication* app, gpointer data)
{
@@ -100,7 +116,25 @@ PrettyTable::on_application_closed(WnckScreen* screen, WnckApplication* app, gpo
static_cast<PrettyTable*>(data)->unregister_application(pid);
}
+void PrettyTable::init_gio_app_cache ()
+{
+ this->gio_apps.clear();
+
+ Glib::ListHandle<Glib::RefPtr<Gio::AppInfo>> registered_apps = Gio::AppInfo::get_all();
+ for (Glib::ListHandle<Glib::RefPtr<Gio::AppInfo>>::const_iterator it = registered_apps.begin(); it != registered_apps.end(); ++it) {
+ Glib::RefPtr<Gio::AppInfo> app = *it;
+ std::string executable = app->get_executable();
+ if (executable != "sh" && executable != "env")
+ this->gio_apps[executable] = app;
+ }
+}
+void PrettyTable::file_monitor_event(Glib::RefPtr<Gio::File>,
+ Glib::RefPtr<Gio::File>,
+ Gio::FileMonitorEvent)
+{
+ this->init_gio_app_cache();
+}
void
PrettyTable::unregister_application(pid_t pid)
@@ -159,7 +193,27 @@ PrettyTable::get_icon_from_default(const ProcInfo &info)
return pix;
}
+Glib::RefPtr<Gdk::Pixbuf>
+PrettyTable::get_icon_from_gio(const ProcInfo &info)
+{
+ gchar **cmdline = g_strsplit(info.name, " ", 2);
+ const gchar *executable = cmdline[0];
+ Glib::RefPtr<Gdk::Pixbuf> icon;
+
+ if (executable) {
+ Glib::RefPtr<Gio::AppInfo> app = this->gio_apps[executable];
+ Glib::RefPtr<Gio::Icon> gicon;
+ if (app)
+ gicon = app->get_icon();
+
+ if (gicon)
+ icon = this->theme->load_gicon(gicon, APP_ICON_SIZE, Gtk::ICON_LOOKUP_USE_BUILTIN | Gtk::ICON_LOOKUP_FORCE_SIZE);
+ }
+
+ g_strfreev(cmdline);
+ return icon;
+}
Glib::RefPtr<Gdk::Pixbuf>
PrettyTable::get_icon_from_wnck(const ProcInfo &info)
@@ -229,6 +283,7 @@ PrettyTable::set_icon(ProcInfo &info)
if (getters.empty())
{
+ getters.push_back(&PrettyTable::get_icon_from_gio);
getters.push_back(&PrettyTable::get_icon_from_wnck);
getters.push_back(&PrettyTable::get_icon_from_theme);
getters.push_back(&PrettyTable::get_icon_from_default);
diff --git a/src/prettytable.h b/src/prettytable.h
index 2109121..ac150de 100644
--- a/src/prettytable.h
+++ b/src/prettytable.h
@@ -7,6 +7,7 @@
#include <gdk-pixbuf/gdk-pixbuf.h>
#include <glibmm/refptr.h>
#include <gdkmm/pixbuf.h>
+#include <giomm/filemonitor.h>
#include <map>
#include <string>
@@ -43,18 +44,28 @@ private:
Glib::RefPtr<Gdk::Pixbuf> get_icon_from_theme(const ProcInfo &);
Glib::RefPtr<Gdk::Pixbuf> get_icon_from_default(const ProcInfo &);
+ Glib::RefPtr<Gdk::Pixbuf> get_icon_from_gio(const ProcInfo &);
Glib::RefPtr<Gdk::Pixbuf> get_icon_from_wnck(const ProcInfo &);
Glib::RefPtr<Gdk::Pixbuf> get_icon_from_name(const ProcInfo &);
Glib::RefPtr<Gdk::Pixbuf> get_icon_for_kernel(const ProcInfo &);
Glib::RefPtr<Gdk::Pixbuf> get_icon_dummy(const ProcInfo &);
bool get_default_icon_name(const string &cmd, string &name);
+ void file_monitor_event (Glib::RefPtr<Gio::File>,
+ Glib::RefPtr<Gio::File>,
+ Gio::FileMonitorEvent);
+ void init_gio_app_cache ();
+
typedef std::map<string, Glib::RefPtr<Gdk::Pixbuf> > IconCache;
typedef std::map<pid_t, Glib::RefPtr<Gdk::Pixbuf> > IconsForPID;
+ typedef std::map<string, Glib::RefPtr<Gio::AppInfo> > AppCache;
+ typedef std::map<string, Glib::RefPtr<Gio::FileMonitor> > DesktopDirMonitors;
IconsForPID apps;
IconCache defaults;
+ DesktopDirMonitors monitors;
+ AppCache gio_apps;
procman::IconThemeWrapper theme;
};