xed/pluma/pluma-plugins-engine.c

862 lines
20 KiB
C
Raw Normal View History

2011-11-07 13:46:58 -06:00
/*
2011-11-07 16:52:18 -06:00
* pluma-plugins-engine.c
* This file is part of pluma
2011-11-07 13:46:58 -06:00
*
2011-11-07 18:10:16 -06:00
* Copyright (C) 2002-2005 Paolo Maggi
2011-11-07 13:46:58 -06:00
*
* This program is free software; you can redistribute it and/or modify
* it under the terms of the GNU General Public License as published by
* the Free Software Foundation; either version 2 of the License, or
* (at your option) any later version.
*
* This program is distributed in the hope that it will be useful,
* but WITHOUT ANY WARRANTY; without even the implied warranty of
* MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the
* GNU General Public License for more details.
*
* You should have received a copy of the GNU General Public License
* along with this program; if not, write to the Free Software
2012-11-18 19:54:49 -06:00
* Foundation, Inc., 51 Franklin St, Fifth Floor,
* Boston, MA 02110-1301, USA.
2011-11-07 13:46:58 -06:00
*/
/*
2011-11-07 18:10:16 -06:00
* Modified by the pluma Team, 2002-2005. See the AUTHORS file for a
* list of people on the pluma Team.
* See the ChangeLog files for a list of changes.
2011-11-07 13:46:58 -06:00
*
* $Id$
*/
#ifdef HAVE_CONFIG_H
#include <config.h>
#endif
#include <string.h>
#include <glib/gi18n.h>
2011-11-07 16:52:18 -06:00
#include "pluma-plugins-engine.h"
#include "pluma-plugin-info-priv.h"
#include "pluma-plugin.h"
#include "pluma-debug.h"
#include "pluma-app.h"
#include "pluma-prefs-manager.h"
#include "pluma-plugin-loader.h"
#include "pluma-object-module.h"
#include "pluma-dirs.h"
2011-11-07 13:46:58 -06:00
2011-11-07 18:10:16 -06:00
#define PLUMA_PLUGINS_ENGINE_BASE_KEY "/apps/pluma/plugins"
2011-11-07 16:52:18 -06:00
#define PLUMA_PLUGINS_ENGINE_KEY PLUMA_PLUGINS_ENGINE_BASE_KEY "/active-plugins"
2011-11-07 13:46:58 -06:00
2011-11-07 16:52:18 -06:00
#define PLUGIN_EXT ".pluma-plugin"
2011-11-07 13:46:58 -06:00
#define LOADER_EXT G_MODULE_SUFFIX
typedef struct
{
2011-11-07 16:52:18 -06:00
PlumaPluginLoader *loader;
PlumaObjectModule *module;
2011-11-07 13:46:58 -06:00
} LoaderInfo;
/* Signals */
enum
{
ACTIVATE_PLUGIN,
DEACTIVATE_PLUGIN,
LAST_SIGNAL
};
static guint signals[LAST_SIGNAL];
2011-11-07 16:52:18 -06:00
G_DEFINE_TYPE(PlumaPluginsEngine, pluma_plugins_engine, G_TYPE_OBJECT)
2011-11-07 13:46:58 -06:00
2011-11-07 16:52:18 -06:00
struct _PlumaPluginsEnginePrivate
2011-11-07 13:46:58 -06:00
{
GList *plugin_list;
GHashTable *loaders;
gboolean activate_from_prefs;
};
2011-11-07 16:52:18 -06:00
PlumaPluginsEngine *default_engine = NULL;
2011-11-07 13:46:58 -06:00
2011-11-07 16:52:18 -06:00
static void pluma_plugins_engine_activate_plugin_real (PlumaPluginsEngine *engine,
PlumaPluginInfo *info);
static void pluma_plugins_engine_deactivate_plugin_real (PlumaPluginsEngine *engine,
PlumaPluginInfo *info);
2011-11-07 13:46:58 -06:00
2011-11-07 16:52:18 -06:00
typedef gboolean (*LoadDirCallback)(PlumaPluginsEngine *engine, const gchar *filename, gpointer userdata);
2011-11-07 13:46:58 -06:00
static gboolean
2011-11-07 16:52:18 -06:00
load_dir_real (PlumaPluginsEngine *engine,
2011-11-07 13:46:58 -06:00
const gchar *dir,
const gchar *suffix,
LoadDirCallback callback,
gpointer userdata)
{
GError *error = NULL;
GDir *d;
const gchar *dirent;
gboolean ret = TRUE;
g_return_val_if_fail (dir != NULL, TRUE);
2011-11-07 16:52:18 -06:00
pluma_debug_message (DEBUG_PLUGINS, "DIR: %s", dir);
2011-11-07 13:46:58 -06:00
d = g_dir_open (dir, 0, &error);
if (!d)
{
g_warning ("%s", error->message);
g_error_free (error);
return TRUE;
}
2011-11-07 18:10:16 -06:00
2011-11-07 13:46:58 -06:00
while ((dirent = g_dir_read_name (d)))
{
gchar *filename;
if (!g_str_has_suffix (dirent, suffix))
continue;
filename = g_build_filename (dir, dirent, NULL);
ret = callback (engine, filename, userdata);
g_free (filename);
if (!ret)
break;
}
g_dir_close (d);
return ret;
}
static gboolean
2011-11-07 16:52:18 -06:00
load_plugin_info (PlumaPluginsEngine *engine,
2011-11-07 13:46:58 -06:00
const gchar *filename,
gpointer userdata)
{
2011-11-07 16:52:18 -06:00
PlumaPluginInfo *info;
2011-11-07 18:10:16 -06:00
2011-11-07 16:52:18 -06:00
info = _pluma_plugin_info_new (filename);
2011-11-07 13:46:58 -06:00
if (info == NULL)
return TRUE;
/* If a plugin with this name has already been loaded
* drop this one (user plugins override system plugins) */
2011-11-07 16:52:18 -06:00
if (pluma_plugins_engine_get_plugin_info (engine, pluma_plugin_info_get_module_name (info)) != NULL)
2011-11-07 13:46:58 -06:00
{
2011-11-07 16:52:18 -06:00
pluma_debug_message (DEBUG_PLUGINS, "Two or more plugins named '%s'. "
2011-11-07 13:46:58 -06:00
"Only the first will be considered.\n",
2011-11-07 16:52:18 -06:00
pluma_plugin_info_get_module_name (info));
2011-11-07 13:46:58 -06:00
2011-11-07 16:52:18 -06:00
_pluma_plugin_info_unref (info);
2011-11-07 13:46:58 -06:00
return TRUE;
}
engine->priv->plugin_list = g_list_prepend (engine->priv->plugin_list, info);
2011-11-07 16:52:18 -06:00
pluma_debug_message (DEBUG_PLUGINS, "Plugin %s loaded", info->name);
2011-11-07 13:46:58 -06:00
return TRUE;
}
static void
2011-11-07 16:52:18 -06:00
load_all_plugins (PlumaPluginsEngine *engine)
2011-11-07 13:46:58 -06:00
{
gchar *plugin_dir;
const gchar *pdirs_env = NULL;
/* load user plugins */
2011-11-07 16:52:18 -06:00
plugin_dir = pluma_dirs_get_user_plugins_dir ();
2011-11-07 13:46:58 -06:00
if (g_file_test (plugin_dir, G_FILE_TEST_IS_DIR))
{
load_dir_real (engine,
plugin_dir,
PLUGIN_EXT,
load_plugin_info,
NULL);
}
g_free (plugin_dir);
/* load system plugins */
2011-11-07 16:52:18 -06:00
pdirs_env = g_getenv ("PLUMA_PLUGINS_PATH");
2011-11-07 13:46:58 -06:00
2011-11-07 16:52:18 -06:00
pluma_debug_message (DEBUG_PLUGINS, "PLUMA_PLUGINS_PATH=%s", pdirs_env);
2011-11-07 13:46:58 -06:00
if (pdirs_env != NULL)
{
gchar **pdirs;
gint i;
pdirs = g_strsplit (pdirs_env, G_SEARCHPATH_SEPARATOR_S, 0);
for (i = 0; pdirs[i] != NULL; i++)
{
if (!load_dir_real (engine,
pdirs[i],
PLUGIN_EXT,
load_plugin_info,
NULL))
{
break;
}
}
g_strfreev (pdirs);
}
else
{
2011-11-07 16:52:18 -06:00
plugin_dir = pluma_dirs_get_pluma_plugins_dir ();
2011-11-07 13:46:58 -06:00
load_dir_real (engine,
plugin_dir,
PLUGIN_EXT,
load_plugin_info,
NULL);
g_free (plugin_dir);
}
}
static guint
hash_lowercase (gconstpointer data)
{
gchar *lowercase;
guint ret;
2011-11-07 18:10:16 -06:00
2011-11-07 13:46:58 -06:00
lowercase = g_ascii_strdown ((const gchar *)data, -1);
ret = g_str_hash (lowercase);
g_free (lowercase);
2011-11-07 18:10:16 -06:00
2011-11-07 13:46:58 -06:00
return ret;
}
static gboolean
equal_lowercase (gconstpointer a, gconstpointer b)
{
return g_ascii_strcasecmp ((const gchar *)a, (const gchar *)b) == 0;
}
static void
loader_destroy (LoaderInfo *info)
{
if (!info)
return;
2011-11-07 18:10:16 -06:00
2011-11-07 13:46:58 -06:00
if (info->loader)
g_object_unref (info->loader);
2011-11-07 18:10:16 -06:00
2011-11-07 13:46:58 -06:00
g_free (info);
}
static void
2011-11-07 16:52:18 -06:00
add_loader (PlumaPluginsEngine *engine,
2011-11-07 13:46:58 -06:00
const gchar *loader_id,
2011-11-07 16:52:18 -06:00
PlumaObjectModule *module)
2011-11-07 13:46:58 -06:00
{
LoaderInfo *info;
info = g_new (LoaderInfo, 1);
info->loader = NULL;
info->module = module;
g_hash_table_insert (engine->priv->loaders, g_strdup (loader_id), info);
}
static void
2011-11-07 16:52:18 -06:00
pluma_plugins_engine_init (PlumaPluginsEngine *engine)
2011-11-07 13:46:58 -06:00
{
2011-11-07 16:52:18 -06:00
pluma_debug (DEBUG_PLUGINS);
2011-11-07 13:46:58 -06:00
if (!g_module_supported ())
{
2011-11-07 16:52:18 -06:00
g_warning ("pluma is not able to initialize the plugins engine.");
2011-11-07 13:46:58 -06:00
return;
}
engine->priv = G_TYPE_INSTANCE_GET_PRIVATE (engine,
2011-11-07 16:52:18 -06:00
PLUMA_TYPE_PLUGINS_ENGINE,
PlumaPluginsEnginePrivate);
2011-11-07 13:46:58 -06:00
load_all_plugins (engine);
/* make sure that the first reactivation will read active plugins
from the prefs */
engine->priv->activate_from_prefs = TRUE;
/* mapping from loadername -> loader object */
engine->priv->loaders = g_hash_table_new_full (hash_lowercase,
equal_lowercase,
(GDestroyNotify)g_free,
(GDestroyNotify)loader_destroy);
}
static void
loader_garbage_collect (const char *id, LoaderInfo *info)
{
if (info->loader)
2011-11-07 16:52:18 -06:00
pluma_plugin_loader_garbage_collect (info->loader);
2011-11-07 13:46:58 -06:00
}
void
2011-11-07 16:52:18 -06:00
pluma_plugins_engine_garbage_collect (PlumaPluginsEngine *engine)
2011-11-07 13:46:58 -06:00
{
g_hash_table_foreach (engine->priv->loaders,
(GHFunc) loader_garbage_collect,
NULL);
}
static void
2011-11-07 16:52:18 -06:00
pluma_plugins_engine_finalize (GObject *object)
2011-11-07 13:46:58 -06:00
{
2011-11-07 16:52:18 -06:00
PlumaPluginsEngine *engine = PLUMA_PLUGINS_ENGINE (object);
2011-11-07 13:46:58 -06:00
GList *item;
2011-11-07 18:10:16 -06:00
2011-11-07 16:52:18 -06:00
pluma_debug (DEBUG_PLUGINS);
2011-11-07 13:46:58 -06:00
/* Firs deactivate all plugins */
for (item = engine->priv->plugin_list; item; item = item->next)
{
2011-11-07 16:52:18 -06:00
PlumaPluginInfo *info = PLUMA_PLUGIN_INFO (item->data);
2011-11-07 18:10:16 -06:00
2011-11-07 16:52:18 -06:00
if (pluma_plugin_info_is_active (info))
pluma_plugins_engine_deactivate_plugin_real (engine, info);
2011-11-07 13:46:58 -06:00
}
2011-11-07 18:10:16 -06:00
/* unref the loaders */
2011-11-07 13:46:58 -06:00
g_hash_table_destroy (engine->priv->loaders);
/* and finally free the infos */
for (item = engine->priv->plugin_list; item; item = item->next)
{
2011-11-07 16:52:18 -06:00
PlumaPluginInfo *info = PLUMA_PLUGIN_INFO (item->data);
2011-11-07 13:46:58 -06:00
2011-11-07 16:52:18 -06:00
_pluma_plugin_info_unref (info);
2011-11-07 13:46:58 -06:00
}
g_list_free (engine->priv->plugin_list);
2011-11-07 16:52:18 -06:00
G_OBJECT_CLASS (pluma_plugins_engine_parent_class)->finalize (object);
2011-11-07 13:46:58 -06:00
}
static void
2011-11-07 16:52:18 -06:00
pluma_plugins_engine_class_init (PlumaPluginsEngineClass *klass)
2011-11-07 13:46:58 -06:00
{
GType the_type = G_TYPE_FROM_CLASS (klass);
GObjectClass *object_class = G_OBJECT_CLASS (klass);
2011-11-07 16:52:18 -06:00
object_class->finalize = pluma_plugins_engine_finalize;
klass->activate_plugin = pluma_plugins_engine_activate_plugin_real;
klass->deactivate_plugin = pluma_plugins_engine_deactivate_plugin_real;
2011-11-07 13:46:58 -06:00
signals[ACTIVATE_PLUGIN] =
g_signal_new ("activate-plugin",
the_type,
G_SIGNAL_RUN_LAST,
2011-11-07 16:52:18 -06:00
G_STRUCT_OFFSET (PlumaPluginsEngineClass, activate_plugin),
2011-11-07 13:46:58 -06:00
NULL, NULL,
g_cclosure_marshal_VOID__BOXED,
G_TYPE_NONE,
1,
2011-11-07 16:52:18 -06:00
PLUMA_TYPE_PLUGIN_INFO | G_SIGNAL_TYPE_STATIC_SCOPE);
2011-11-07 13:46:58 -06:00
signals[DEACTIVATE_PLUGIN] =
g_signal_new ("deactivate-plugin",
the_type,
G_SIGNAL_RUN_LAST,
2011-11-07 16:52:18 -06:00
G_STRUCT_OFFSET (PlumaPluginsEngineClass, deactivate_plugin),
2011-11-07 13:46:58 -06:00
NULL, NULL,
g_cclosure_marshal_VOID__BOXED,
G_TYPE_NONE,
1,
2011-11-07 16:52:18 -06:00
PLUMA_TYPE_PLUGIN_INFO | G_SIGNAL_TYPE_STATIC_SCOPE);
2011-11-07 13:46:58 -06:00
2011-11-07 16:52:18 -06:00
g_type_class_add_private (klass, sizeof (PlumaPluginsEnginePrivate));
2011-11-07 13:46:58 -06:00
}
static gboolean
2011-11-07 16:52:18 -06:00
load_loader (PlumaPluginsEngine *engine,
2011-11-07 13:46:58 -06:00
const gchar *filename,
gpointer data)
{
2011-11-07 16:52:18 -06:00
PlumaObjectModule *module;
2011-11-07 13:46:58 -06:00
gchar *base;
gchar *path;
const gchar *id;
GType type;
2011-11-07 18:10:16 -06:00
2011-11-07 13:46:58 -06:00
/* try to load in the module */
path = g_path_get_dirname (filename);
base = g_path_get_basename (filename);
/* for now they are all resident */
2011-11-07 16:52:18 -06:00
module = pluma_object_module_new (base,
2011-11-07 13:46:58 -06:00
path,
2011-11-07 16:52:18 -06:00
"register_pluma_plugin_loader",
2011-11-07 13:46:58 -06:00
TRUE);
g_free (base);
g_free (path);
/* make sure to load the type definition */
if (!g_type_module_use (G_TYPE_MODULE (module)))
{
g_object_unref (module);
g_warning ("Plugin loader module `%s' could not be loaded", filename);
return TRUE;
}
2011-11-07 18:10:16 -06:00
/* get the exported type and check the name as exported by the
2011-11-07 13:46:58 -06:00
* loader interface */
2011-11-07 16:52:18 -06:00
type = pluma_object_module_get_object_type (module);
id = pluma_plugin_loader_type_get_id (type);
2011-11-07 18:10:16 -06:00
add_loader (engine, id, module);
2011-11-07 13:46:58 -06:00
g_type_module_unuse (G_TYPE_MODULE (module));
return TRUE;
}
static void
ensure_loader (LoaderInfo *info)
{
if (info->loader == NULL && info->module != NULL)
{
/* create a new loader object */
2011-11-07 16:52:18 -06:00
PlumaPluginLoader *loader;
loader = (PlumaPluginLoader *)pluma_object_module_new_object (info->module, NULL);
2011-11-07 18:10:16 -06:00
2011-11-07 16:52:18 -06:00
if (loader == NULL || !PLUMA_IS_PLUGIN_LOADER (loader))
2011-11-07 13:46:58 -06:00
{
2011-11-07 16:52:18 -06:00
g_warning ("Loader object is not a valid PlumaPluginLoader instance");
2011-11-07 18:10:16 -06:00
2011-11-07 13:46:58 -06:00
if (loader != NULL && G_IS_OBJECT (loader))
g_object_unref (loader);
}
else
{
info->loader = loader;
}
}
}
2011-11-07 16:52:18 -06:00
static PlumaPluginLoader *
get_plugin_loader (PlumaPluginsEngine *engine, PlumaPluginInfo *info)
2011-11-07 13:46:58 -06:00
{
const gchar *loader_id;
LoaderInfo *loader_info;
loader_id = info->loader;
loader_info = (LoaderInfo *)g_hash_table_lookup (
2011-11-07 18:10:16 -06:00
engine->priv->loaders,
2011-11-07 13:46:58 -06:00
loader_id);
if (loader_info == NULL)
{
gchar *loader_dir;
2011-11-07 16:52:18 -06:00
loader_dir = pluma_dirs_get_pluma_plugin_loaders_dir ();
2011-11-07 13:46:58 -06:00
2011-11-07 18:10:16 -06:00
/* loader could not be found in the hash, try to find it by
2011-11-07 13:46:58 -06:00
scanning */
2011-11-07 18:10:16 -06:00
load_dir_real (engine,
2011-11-07 13:46:58 -06:00
loader_dir,
LOADER_EXT,
(LoadDirCallback)load_loader,
NULL);
g_free (loader_dir);
2011-11-07 18:10:16 -06:00
2011-11-07 13:46:58 -06:00
loader_info = (LoaderInfo *)g_hash_table_lookup (
2011-11-07 18:10:16 -06:00
engine->priv->loaders,
2011-11-07 13:46:58 -06:00
loader_id);
}
if (loader_info == NULL)
{
/* cache non-existent so we don't scan again */
add_loader (engine, loader_id, NULL);
return NULL;
}
2011-11-07 18:10:16 -06:00
2011-11-07 13:46:58 -06:00
ensure_loader (loader_info);
return loader_info->loader;
}
2011-11-07 16:52:18 -06:00
PlumaPluginsEngine *
pluma_plugins_engine_get_default (void)
2011-11-07 13:46:58 -06:00
{
if (default_engine != NULL)
return default_engine;
2011-11-07 16:52:18 -06:00
default_engine = PLUMA_PLUGINS_ENGINE (g_object_new (PLUMA_TYPE_PLUGINS_ENGINE, NULL));
2011-11-07 13:46:58 -06:00
g_object_add_weak_pointer (G_OBJECT (default_engine),
(gpointer) &default_engine);
return default_engine;
}
const GList *
2011-11-07 16:52:18 -06:00
pluma_plugins_engine_get_plugin_list (PlumaPluginsEngine *engine)
2011-11-07 13:46:58 -06:00
{
2011-11-07 16:52:18 -06:00
pluma_debug (DEBUG_PLUGINS);
2011-11-07 13:46:58 -06:00
return engine->priv->plugin_list;
}
static gint
2011-11-07 16:52:18 -06:00
compare_plugin_info_and_name (PlumaPluginInfo *info,
2011-11-07 13:46:58 -06:00
const gchar *module_name)
{
2011-11-07 16:52:18 -06:00
return strcmp (pluma_plugin_info_get_module_name (info), module_name);
2011-11-07 13:46:58 -06:00
}
2011-11-07 16:52:18 -06:00
PlumaPluginInfo *
pluma_plugins_engine_get_plugin_info (PlumaPluginsEngine *engine,
2011-11-07 13:46:58 -06:00
const gchar *name)
{
GList *l = g_list_find_custom (engine->priv->plugin_list,
name,
(GCompareFunc) compare_plugin_info_and_name);
2011-11-07 16:52:18 -06:00
return l == NULL ? NULL : (PlumaPluginInfo *) l->data;
2011-11-07 13:46:58 -06:00
}
static void
2011-11-07 16:52:18 -06:00
save_active_plugin_list (PlumaPluginsEngine *engine)
2011-11-07 13:46:58 -06:00
{
GSList *active_plugins = NULL;
GList *l;
for (l = engine->priv->plugin_list; l != NULL; l = l->next)
{
2011-11-07 16:52:18 -06:00
PlumaPluginInfo *info = (PlumaPluginInfo *) l->data;
2011-11-07 13:46:58 -06:00
2011-11-07 16:52:18 -06:00
if (pluma_plugin_info_is_active (info))
2011-11-07 13:46:58 -06:00
{
active_plugins = g_slist_prepend (active_plugins,
2011-11-07 16:52:18 -06:00
(gpointer)pluma_plugin_info_get_module_name (info));
2011-11-07 13:46:58 -06:00
}
}
2011-11-07 16:52:18 -06:00
pluma_prefs_manager_set_active_plugins (active_plugins);
2011-11-07 13:46:58 -06:00
g_slist_free (active_plugins);
}
static gboolean
2011-11-07 16:52:18 -06:00
load_plugin (PlumaPluginsEngine *engine,
PlumaPluginInfo *info)
2011-11-07 13:46:58 -06:00
{
2011-11-07 16:52:18 -06:00
PlumaPluginLoader *loader;
2011-11-07 13:46:58 -06:00
gchar *path;
2011-11-07 16:52:18 -06:00
if (pluma_plugin_info_is_active (info))
2011-11-07 13:46:58 -06:00
return TRUE;
2011-11-07 18:10:16 -06:00
2011-11-07 16:52:18 -06:00
if (!pluma_plugin_info_is_available (info))
2011-11-07 13:46:58 -06:00
return FALSE;
loader = get_plugin_loader (engine, info);
2011-11-07 18:10:16 -06:00
2011-11-07 13:46:58 -06:00
if (loader == NULL)
{
g_warning ("Could not find loader `%s' for plugin `%s'", info->loader, info->name);
info->available = FALSE;
return FALSE;
}
2011-11-07 18:10:16 -06:00
2011-11-07 13:46:58 -06:00
path = g_path_get_dirname (info->file);
g_return_val_if_fail (path != NULL, FALSE);
2011-11-07 16:52:18 -06:00
info->plugin = pluma_plugin_loader_load (loader, info, path);
2011-11-07 18:10:16 -06:00
2011-11-07 13:46:58 -06:00
g_free (path);
2011-11-07 18:10:16 -06:00
2011-11-07 13:46:58 -06:00
if (info->plugin == NULL)
{
g_warning ("Error loading plugin '%s'", info->name);
info->available = FALSE;
return FALSE;
}
2011-11-07 18:10:16 -06:00
2011-11-07 13:46:58 -06:00
return TRUE;
}
static void
2011-11-07 16:52:18 -06:00
pluma_plugins_engine_activate_plugin_real (PlumaPluginsEngine *engine,
PlumaPluginInfo *info)
2011-11-07 13:46:58 -06:00
{
const GList *wins;
if (!load_plugin (engine, info))
return;
2011-11-07 16:52:18 -06:00
for (wins = pluma_app_get_windows (pluma_app_get_default ());
2011-11-07 13:46:58 -06:00
wins != NULL;
wins = wins->next)
{
2011-11-07 16:52:18 -06:00
pluma_plugin_activate (info->plugin, PLUMA_WINDOW (wins->data));
2011-11-07 13:46:58 -06:00
}
}
gboolean
2011-11-07 16:52:18 -06:00
pluma_plugins_engine_activate_plugin (PlumaPluginsEngine *engine,
PlumaPluginInfo *info)
2011-11-07 13:46:58 -06:00
{
2011-11-07 16:52:18 -06:00
pluma_debug (DEBUG_PLUGINS);
2011-11-07 13:46:58 -06:00
g_return_val_if_fail (info != NULL, FALSE);
2011-11-07 16:52:18 -06:00
if (!pluma_plugin_info_is_available (info))
2011-11-07 13:46:58 -06:00
return FALSE;
2011-11-07 18:10:16 -06:00
2011-11-07 16:52:18 -06:00
if (pluma_plugin_info_is_active (info))
2011-11-07 13:46:58 -06:00
return TRUE;
g_signal_emit (engine, signals[ACTIVATE_PLUGIN], 0, info);
2011-11-07 16:52:18 -06:00
if (pluma_plugin_info_is_active (info))
2011-11-07 13:46:58 -06:00
save_active_plugin_list (engine);
2011-11-07 16:52:18 -06:00
return pluma_plugin_info_is_active (info);
2011-11-07 13:46:58 -06:00
}
static void
2011-11-07 18:10:16 -06:00
call_plugin_deactivate (PlumaPlugin *plugin,
2011-11-07 16:52:18 -06:00
PlumaWindow *window)
2011-11-07 13:46:58 -06:00
{
2011-11-07 16:52:18 -06:00
pluma_plugin_deactivate (plugin, window);
2011-11-07 13:46:58 -06:00
/* ensure update of ui manager, because we suspect it does something
with expected static strings in the type module (when unloaded the
strings don't exist anymore, and ui manager updates in an idle
func) */
2011-11-07 16:52:18 -06:00
gtk_ui_manager_ensure_update (pluma_window_get_ui_manager (window));
2011-11-07 13:46:58 -06:00
}
static void
2011-11-07 16:52:18 -06:00
pluma_plugins_engine_deactivate_plugin_real (PlumaPluginsEngine *engine,
PlumaPluginInfo *info)
2011-11-07 13:46:58 -06:00
{
const GList *wins;
2011-11-07 16:52:18 -06:00
PlumaPluginLoader *loader;
2011-11-07 13:46:58 -06:00
2011-11-07 18:10:16 -06:00
if (!pluma_plugin_info_is_active (info) ||
2011-11-07 16:52:18 -06:00
!pluma_plugin_info_is_available (info))
2011-11-07 13:46:58 -06:00
return;
2011-11-07 16:52:18 -06:00
for (wins = pluma_app_get_windows (pluma_app_get_default ());
2011-11-07 13:46:58 -06:00
wins != NULL;
wins = wins->next)
{
2011-11-07 16:52:18 -06:00
call_plugin_deactivate (info->plugin, PLUMA_WINDOW (wins->data));
2011-11-07 13:46:58 -06:00
}
/* first unref the plugin (the loader still has one) */
g_object_unref (info->plugin);
2011-11-07 18:10:16 -06:00
2011-11-07 13:46:58 -06:00
/* find the loader and tell it to gc and unload the plugin */
loader = get_plugin_loader (engine, info);
2011-11-07 18:10:16 -06:00
2011-11-07 16:52:18 -06:00
pluma_plugin_loader_garbage_collect (loader);
pluma_plugin_loader_unload (loader, info);
2011-11-07 18:10:16 -06:00
2011-11-07 13:46:58 -06:00
info->plugin = NULL;
}
gboolean
2011-11-07 16:52:18 -06:00
pluma_plugins_engine_deactivate_plugin (PlumaPluginsEngine *engine,
PlumaPluginInfo *info)
2011-11-07 13:46:58 -06:00
{
2011-11-07 16:52:18 -06:00
pluma_debug (DEBUG_PLUGINS);
2011-11-07 13:46:58 -06:00
g_return_val_if_fail (info != NULL, FALSE);
2011-11-07 16:52:18 -06:00
if (!pluma_plugin_info_is_active (info))
2011-11-07 13:46:58 -06:00
return TRUE;
g_signal_emit (engine, signals[DEACTIVATE_PLUGIN], 0, info);
2011-11-07 16:52:18 -06:00
if (!pluma_plugin_info_is_active (info))
2011-11-07 13:46:58 -06:00
save_active_plugin_list (engine);
2011-11-07 16:52:18 -06:00
return !pluma_plugin_info_is_active (info);
2011-11-07 13:46:58 -06:00
}
void
2011-11-07 16:52:18 -06:00
pluma_plugins_engine_activate_plugins (PlumaPluginsEngine *engine,
PlumaWindow *window)
2011-11-07 13:46:58 -06:00
{
GSList *active_plugins = NULL;
GList *pl;
2011-11-07 16:52:18 -06:00
pluma_debug (DEBUG_PLUGINS);
2011-11-07 13:46:58 -06:00
2011-11-07 16:52:18 -06:00
g_return_if_fail (PLUMA_IS_PLUGINS_ENGINE (engine));
g_return_if_fail (PLUMA_IS_WINDOW (window));
2011-11-07 13:46:58 -06:00
2013-01-24 14:03:53 -06:00
/* the first time, we get the 'active' plugins from GSettings */
2011-11-07 13:46:58 -06:00
if (engine->priv->activate_from_prefs)
{
2011-11-07 16:52:18 -06:00
active_plugins = pluma_prefs_manager_get_active_plugins ();
2011-11-07 13:46:58 -06:00
}
for (pl = engine->priv->plugin_list; pl; pl = pl->next)
{
2011-11-07 16:52:18 -06:00
PlumaPluginInfo *info = (PlumaPluginInfo*)pl->data;
2011-11-07 18:10:16 -06:00
if (engine->priv->activate_from_prefs &&
2011-11-07 13:46:58 -06:00
g_slist_find_custom (active_plugins,
2011-11-07 16:52:18 -06:00
pluma_plugin_info_get_module_name (info),
2011-11-07 13:46:58 -06:00
(GCompareFunc)strcmp) == NULL)
continue;
2011-11-07 18:10:16 -06:00
2011-11-07 13:46:58 -06:00
/* If plugin is not active, don't try to activate/load it */
2011-11-07 18:10:16 -06:00
if (!engine->priv->activate_from_prefs &&
2011-11-07 16:52:18 -06:00
!pluma_plugin_info_is_active (info))
2011-11-07 13:46:58 -06:00
continue;
if (load_plugin (engine, info))
2011-11-07 16:52:18 -06:00
pluma_plugin_activate (info->plugin,
2011-11-07 13:46:58 -06:00
window);
}
2011-11-07 18:10:16 -06:00
2011-11-07 13:46:58 -06:00
if (engine->priv->activate_from_prefs)
{
g_slist_foreach (active_plugins, (GFunc) g_free, NULL);
g_slist_free (active_plugins);
engine->priv->activate_from_prefs = FALSE;
}
2011-11-07 18:10:16 -06:00
2011-11-07 16:52:18 -06:00
pluma_debug_message (DEBUG_PLUGINS, "End");
2011-11-07 13:46:58 -06:00
/* also call update_ui after activation */
2011-11-07 16:52:18 -06:00
pluma_plugins_engine_update_plugins_ui (engine, window);
2011-11-07 13:46:58 -06:00
}
void
2011-11-07 16:52:18 -06:00
pluma_plugins_engine_deactivate_plugins (PlumaPluginsEngine *engine,
PlumaWindow *window)
2011-11-07 13:46:58 -06:00
{
GList *pl;
2011-11-07 18:10:16 -06:00
2011-11-07 16:52:18 -06:00
pluma_debug (DEBUG_PLUGINS);
2011-11-07 13:46:58 -06:00
2011-11-07 16:52:18 -06:00
g_return_if_fail (PLUMA_IS_PLUGINS_ENGINE (engine));
g_return_if_fail (PLUMA_IS_WINDOW (window));
2011-11-07 18:10:16 -06:00
2011-11-07 13:46:58 -06:00
for (pl = engine->priv->plugin_list; pl; pl = pl->next)
{
2011-11-07 16:52:18 -06:00
PlumaPluginInfo *info = (PlumaPluginInfo*)pl->data;
2011-11-07 18:10:16 -06:00
2011-11-07 13:46:58 -06:00
/* check if the plugin is actually active */
2011-11-07 16:52:18 -06:00
if (!pluma_plugin_info_is_active (info))
2011-11-07 13:46:58 -06:00
continue;
2011-11-07 18:10:16 -06:00
2011-11-07 13:46:58 -06:00
/* call deactivate for the plugin for this window */
2011-11-07 16:52:18 -06:00
pluma_plugin_deactivate (info->plugin, window);
2011-11-07 13:46:58 -06:00
}
2011-11-07 18:10:16 -06:00
2011-11-07 16:52:18 -06:00
pluma_debug_message (DEBUG_PLUGINS, "End");
2011-11-07 13:46:58 -06:00
}
void
2011-11-07 16:52:18 -06:00
pluma_plugins_engine_update_plugins_ui (PlumaPluginsEngine *engine,
PlumaWindow *window)
2011-11-07 13:46:58 -06:00
{
GList *pl;
2011-11-07 16:52:18 -06:00
pluma_debug (DEBUG_PLUGINS);
2011-11-07 13:46:58 -06:00
2011-11-07 16:52:18 -06:00
g_return_if_fail (PLUMA_IS_PLUGINS_ENGINE (engine));
g_return_if_fail (PLUMA_IS_WINDOW (window));
2011-11-07 13:46:58 -06:00
/* call update_ui for all active plugins */
for (pl = engine->priv->plugin_list; pl; pl = pl->next)
{
2011-11-07 16:52:18 -06:00
PlumaPluginInfo *info = (PlumaPluginInfo*)pl->data;
2011-11-07 13:46:58 -06:00
2011-11-07 16:52:18 -06:00
if (!pluma_plugin_info_is_active (info))
2011-11-07 13:46:58 -06:00
continue;
2011-11-07 18:10:16 -06:00
2011-11-07 16:52:18 -06:00
pluma_debug_message (DEBUG_PLUGINS, "Updating UI of %s", info->name);
pluma_plugin_update_ui (info->plugin, window);
2011-11-07 13:46:58 -06:00
}
}
2011-11-07 18:10:16 -06:00
void
2011-11-07 16:52:18 -06:00
pluma_plugins_engine_configure_plugin (PlumaPluginsEngine *engine,
PlumaPluginInfo *info,
2011-11-07 13:46:58 -06:00
GtkWindow *parent)
{
GtkWidget *conf_dlg;
2011-11-07 18:10:16 -06:00
2011-11-07 13:46:58 -06:00
GtkWindowGroup *wg;
2011-11-07 18:10:16 -06:00
2011-11-07 16:52:18 -06:00
pluma_debug (DEBUG_PLUGINS);
2011-11-07 13:46:58 -06:00
g_return_if_fail (info != NULL);
2011-11-07 16:52:18 -06:00
conf_dlg = pluma_plugin_create_configure_dialog (info->plugin);
2011-11-07 13:46:58 -06:00
g_return_if_fail (conf_dlg != NULL);
gtk_window_set_transient_for (GTK_WINDOW (conf_dlg),
parent);
wg = gtk_window_get_group (parent);
if (wg == NULL)
{
wg = gtk_window_group_new ();
gtk_window_group_add_window (wg, parent);
}
2011-11-07 18:10:16 -06:00
2011-11-07 13:46:58 -06:00
gtk_window_group_add_window (wg,
GTK_WINDOW (conf_dlg));
2011-11-07 18:10:16 -06:00
gtk_window_set_modal (GTK_WINDOW (conf_dlg), TRUE);
2011-11-07 13:46:58 -06:00
gtk_widget_show (conf_dlg);
}
2011-11-07 18:10:16 -06:00
void
2011-11-07 16:52:18 -06:00
pluma_plugins_engine_active_plugins_changed (PlumaPluginsEngine *engine)
2011-11-07 13:46:58 -06:00
{
gboolean to_activate;
GSList *active_plugins;
GList *pl;
2011-11-07 16:52:18 -06:00
pluma_debug (DEBUG_PLUGINS);
2011-11-07 13:46:58 -06:00
2011-11-07 16:52:18 -06:00
active_plugins = pluma_prefs_manager_get_active_plugins ();
2011-11-07 13:46:58 -06:00
for (pl = engine->priv->plugin_list; pl; pl = pl->next)
{
2011-11-07 16:52:18 -06:00
PlumaPluginInfo *info = (PlumaPluginInfo*)pl->data;
2011-11-07 13:46:58 -06:00
2011-11-07 16:52:18 -06:00
if (!pluma_plugin_info_is_available (info))
2011-11-07 13:46:58 -06:00
continue;
to_activate = (g_slist_find_custom (active_plugins,
2011-11-07 16:52:18 -06:00
pluma_plugin_info_get_module_name (info),
2011-11-07 13:46:58 -06:00
(GCompareFunc)strcmp) != NULL);
2011-11-07 16:52:18 -06:00
if (!pluma_plugin_info_is_active (info) && to_activate)
2011-11-07 13:46:58 -06:00
g_signal_emit (engine, signals[ACTIVATE_PLUGIN], 0, info);
2011-11-07 16:52:18 -06:00
else if (pluma_plugin_info_is_active (info) && !to_activate)
2011-11-07 13:46:58 -06:00
g_signal_emit (engine, signals[DEACTIVATE_PLUGIN], 0, info);
}
g_slist_foreach (active_plugins, (GFunc) g_free, NULL);
g_slist_free (active_plugins);
}
void
2011-11-07 16:52:18 -06:00
pluma_plugins_engine_rescan_plugins (PlumaPluginsEngine *engine)
2011-11-07 13:46:58 -06:00
{
2011-11-07 16:52:18 -06:00
pluma_debug (DEBUG_PLUGINS);
2011-11-07 18:10:16 -06:00
2011-11-07 13:46:58 -06:00
load_all_plugins (engine);
}