/* SciGraphica - Scientific graphics and data manipulation
* Copyright (C) 2001 Adrian E. Feiguin <feiguin@ifir.edu.ar>
*
* 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
* Foundation, Inc., 675 Mass Ave, Cambridge, MA 02139, USA.
*/
#include <stdio.h>
#include <string.h>
#include <gdk/gdk.h>
#include <gtk/gtk.h>
#include <gtkextra/gtkextra.h>
#include "sg_config.h"
#include "sg_plugin.h"
#include "python_main.h"
PyObject *sg_config_dict;
static GHashTable *config_groups;
/* Create groups hashtable, and optionally the python config_dict */
void
sg_config_init()
{
config_groups = g_hash_table_new (g_str_hash, g_str_equal);
sg_config_dict=PyDict_New();
/* Make the configuration details available in python too */
sg_config_dict=PyDict_GetItemString (sg_dict, "config");
if (!sg_config_dict){
sg_config_dict=PyDict_New();
PyDict_SetItemString(sg_dict,"config",sg_config_dict);
}
}
/* Create a new group, if it doesn't exist already, in the sg_config_dict */
static PyObject *
sg_config_group_new_python(gchar *group)
{ PyObject *group_dict;
group_dict=PyDict_GetItemString(sg_config_dict,group);
if (!group_dict) {
group_dict=PyDict_New();
PyDict_SetItemString(sg_config_dict,group,group_dict);
}
return group_dict;
}
/* Create a new group, if it doesn't exist already, in the config_groups */
static GHashTable *
sg_config_group_new_config(gchar *group)
{ GHashTable *group_config;
group_config=(GHashTable*)g_hash_table_lookup(config_groups,group);
if (!group_config) {
group_config=g_hash_table_new(g_str_hash, g_str_equal);
g_hash_table_insert(config_groups,group,group_config);
}
return group_config;
}
/* Remove a configuration item. from the C structures only */
static void
sg_config_destroy_config(SGconfig *config)
{ PyObject *group_dict,*config_item;
if(!config) return;
if(config->name) g_free(config->name);
if(config->group) g_free(config->group);
g_free(config);
}
/* Set the SGconfig structure belonging to the name and group */
static gboolean
sg_config_set_config(gchar *name, gchar *group, SGconfig *config,
gboolean overwrite){
GHashTable *group_config;
SGconfig *oldconfig;
group_config=sg_config_group_new_config(group);
oldconfig=(SGconfig*)g_hash_table_lookup(group_config,name);
if (oldconfig==config) return TRUE;
if (oldconfig && !overwrite)
return FALSE;
else {
g_hash_table_remove(group_config,name);
sg_config_destroy_config(oldconfig);
}
g_hash_table_insert(group_config,name,config);
return TRUE;
}
/* New configuration item */
static SGconfig *
sg_config_new(gchar *name, gchar *group, SGPluginType type, gpointer def,
gpointer commit)
{
SGconfig *config = NULL;
if(!name || !def || !commit || !group) return NULL;
config = g_new0(SGconfig, 1);
config->name = g_strdup(name);
config->group = g_strdup(group);
config->type = (SGConfigType)type;
config->def = (SGConfigFunc)def;
config->commit = (SGConfigFunc)commit;
config->status=SG_CONFIG_NEW;
sg_config_group_new_python(group);
sg_config_set_config(config->name,config->group,config,TRUE); /* always overwrite old value */
return config;
}
/* New configuration item, with python callbacks */
SGconfig *
sg_config_new_python(gchar *name, gchar *group, PyObject *def,
PyObject *commit)
{ SGconfig *config;
config=sg_config_new(name,group,(SGPluginType)SG_PYTHON_CONFIG,
(gpointer)def, (gpointer)commit);
sg_config_exec_default(config);
config->status=SG_CONFIG_INIT;
return config;
}
/* New configuration item, with C callbacks */
SGconfig *
sg_config_new_c(gchar *name, gchar *group, SGConfigFunc def,
SGConfigFunc commit)
{ SGconfig *config;
config= sg_config_new(name,group,(SGPluginType)SG_C_CONFIG,(gpointer)def,
(gpointer)commit);
sg_config_exec_default(config);
config->status=SG_CONFIG_INIT;
return config;
}
/* Remove a configuration item. from the C and python structures */
static void
sg_config_destroy_full(SGconfig *config)
{ PyObject *group_dict,*config_item;
GHashTable *group_config;
if(!config) return;
group_dict=PyDict_GetItemString(sg_config_dict,config->group);
if(!group_dict) return;
PyDict_DelItemString(group_dict,config->name);
group_config=(GHashTable*)g_hash_table_lookup(config_groups,config->group);
if (g_hash_table_lookup(group_config,config->name));
g_hash_table_remove(group_config,config->name);
sg_config_destroy_config(config);
}
/* Query python value, using the name and group as keys */
PyObject *sg_config_get_value(gchar *name, gchar *group){
PyObject *group_dict;
group_dict=PyDict_GetItemString(sg_config_dict,group);
return PyDict_GetItemString(group_dict,name);
}
/* Set the python value */
gboolean sg_config_set_value(gchar *name, gchar *group, PyObject *value, gboolean overwrite){
PyObject *group_dict;
group_dict=sg_config_group_new_python(group);
if (sg_config_get_value(name, group) && !overwrite) return FALSE;
PyDict_SetItemString(group_dict,name,value);
return TRUE;
}
/* Return the SGconfig structure belonging to the name and group */
SGconfig *
sg_config_get_config(gchar *name, gchar *group){
GHashTable *group_config;
group_config=(GHashTable*)g_hash_table_lookup(config_groups,group);
return (SGconfig *)g_hash_table_lookup(group_config,name);
}
/* This function is for use in g_hash_table_foreach_remove */
static gboolean
sg_config_destroy_hash(gpointer key, gpointer value, gpointer data)
{ SGconfig *config;
config=(SGconfig *)value;
if(!config) return TRUE;
sg_config_destroy_config(config);
return TRUE;
}
void
sg_config_exec_default(SGconfig *config){
PyObject *object;
gint retval;
if (!config) return;
switch (config->type){
case SG_PYTHON_CONFIG:
object=PyObject_CallObject((PyObject*)config->def,NULL);
if (object) config->status=SG_CONFIG_INIT;
python_error_report(object);
break;
case SG_C_CONFIG:
retval=config->def(config);
if (retval) config->status=SG_CONFIG_INIT;
break;
}
}
void
sg_config_exec_commit(SGconfig *config){
PyObject *object;
gint retval;
if (!config) return;
switch (config->type){
case SG_PYTHON_CONFIG:
object=PyObject_CallObject((PyObject*)config->commit,NULL);
python_error_report(object);
if (object) config->status=SG_CONFIG_COMMIT;
break;
case SG_C_CONFIG:
config->commit(config);
if (retval) config->status=SG_CONFIG_COMMIT;
break;
}
}
static void
commit_item(gpointer key, gpointer value, gpointer user_data)
{
sg_config_exec_commit((SGconfig*)value);
}
/* Cycle through commit functions within a group, which is a hashtable kept in
the value parameter.
*/
static
void commit_group(gpointer key, gpointer value, gpointer user_data)
{
g_hash_table_foreach ((GHashTable *)value,commit_item,NULL);
}
void
sg_config_exec_commit_all(void)
{
g_hash_table_foreach (config_groups,commit_group,NULL);
}
syntax highlighted by Code2HTML, v. 0.9.1