/*
* Copyright (C) 2006 Sergey V. Udaltsov <svu@gnome.org>
*
* This library is free software; you can redistribute it and/or
* modify it under the terms of the GNU Lesser General Public
* License as published by the Free Software Foundation; either
* version 2 of the License, or (at your option) any later version.
*
* This library 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
* Lesser General Public License for more details.
*
* You should have received a copy of the GNU Lesser General Public
* License along with this library; if not, write to the
* Free Software Foundation, Inc., 59 Temple Place - Suite 330,
* Boston, MA 02111-1307, USA.
*/
#include <config.h>
#include <stdio.h>
#include <string.h>
#include <stdlib.h>
#include <X11/keysym.h>
#include <glib/gi18n-lib.h>
#include <gkbd-desktop-config.h>
#include <gkbd-config-private.h>
/**
* GkbdDesktopConfig:
*/
const gchar GKBD_DESKTOP_CONFIG_KEY_DEFAULT_GROUP[] = "default-group";
const gchar GKBD_DESKTOP_CONFIG_KEY_GROUP_PER_WINDOW[] =
"group-per-window";
const gchar GKBD_DESKTOP_CONFIG_KEY_HANDLE_INDICATORS[] =
"handle-indicators";
const gchar GKBD_DESKTOP_CONFIG_KEY_LAYOUT_NAMES_AS_GROUP_NAMES[]
= "layout-names-as-group-names";
const gchar GKBD_DESKTOP_CONFIG_KEY_LOAD_EXTRA_ITEMS[]
= "load-extra-items";
/*
* static common functions
*/
static gboolean
gkbd_desktop_config_get_lv_descriptions
(GkbdDesktopConfig * config,
XklConfigRegistry * registry,
const gchar ** layout_ids,
const gchar ** variant_ids,
gchar *** short_layout_descriptions,
gchar *** long_layout_descriptions,
gchar *** short_variant_descriptions,
gchar *** long_variant_descriptions) {
const gchar **pl, **pv;
guint total_layouts;
gchar **sld, **lld, **svd, **lvd;
XklConfigItem *item = xkl_config_item_new ();
if (!
(xkl_engine_get_features (config->engine) &
XKLF_MULTIPLE_LAYOUTS_SUPPORTED))
return FALSE;
pl = layout_ids;
pv = variant_ids;
total_layouts = g_strv_length ((char **) layout_ids);
sld = *short_layout_descriptions =
g_new0 (gchar *, total_layouts + 1);
lld = *long_layout_descriptions =
g_new0 (gchar *, total_layouts + 1);
svd = *short_variant_descriptions =
g_new0 (gchar *, total_layouts + 1);
lvd = *long_variant_descriptions =
g_new0 (gchar *, total_layouts + 1);
while (pl != NULL && *pl != NULL) {
xkl_debug (100, "ids: [%s][%s]\n", *pl,
pv == NULL ? NULL : *pv);
g_snprintf (item->name, sizeof item->name, "%s", *pl);
if (xkl_config_registry_find_layout (registry, item)) {
*sld = g_strdup (item->short_description);
*lld = g_strdup (item->description);
} else {
*sld = g_strdup ("");
*lld = g_strdup ("");
}
if (*pv != NULL) {
g_snprintf (item->name, sizeof item->name, "%s",
*pv);
if (xkl_config_registry_find_variant
(registry, *pl, item)) {
*svd = g_strdup (item->short_description);
*lvd = g_strdup (item->description);
} else {
*svd = g_strdup ("");
*lvd = g_strdup ("");
}
} else {
*svd = g_strdup ("");
*lvd = g_strdup ("");
}
xkl_debug (100, "description: [%s][%s][%s][%s]\n",
*sld, *lld, *svd, *lvd);
sld++;
lld++;
svd++;
lvd++;
pl++;
if (*pv != NULL)
pv++;
}
g_object_unref (item);
return TRUE;
}
/*
* extern GkbdDesktopConfig config functions
*/
void
gkbd_desktop_config_init (GkbdDesktopConfig * config, XklEngine * engine)
{
memset (config, 0, sizeof (*config));
config->settings = g_settings_new (GKBD_DESKTOP_SCHEMA);
config->engine = engine;
}
void
gkbd_desktop_config_term (GkbdDesktopConfig * config)
{
g_object_unref (config->settings);
config->settings = NULL;
}
void
gkbd_desktop_config_load (GkbdDesktopConfig * config)
{
config->group_per_app =
g_settings_get_boolean (config->settings,
GKBD_DESKTOP_CONFIG_KEY_GROUP_PER_WINDOW);
xkl_debug (150, "group_per_app: %d\n", config->group_per_app);
config->handle_indicators =
g_settings_get_boolean (config->settings,
GKBD_DESKTOP_CONFIG_KEY_HANDLE_INDICATORS);
xkl_debug (150, "handle_indicators: %d\n",
config->handle_indicators);
config->layout_names_as_group_names =
g_settings_get_boolean (config->settings,
GKBD_DESKTOP_CONFIG_KEY_LAYOUT_NAMES_AS_GROUP_NAMES);
xkl_debug (150, "layout_names_as_group_names: %d\n",
config->layout_names_as_group_names);
config->load_extra_items =
g_settings_get_boolean (config->settings,
GKBD_DESKTOP_CONFIG_KEY_LOAD_EXTRA_ITEMS);
xkl_debug (150, "load_extra_items: %d\n",
config->load_extra_items);
config->default_group =
g_settings_get_int (config->settings,
GKBD_DESKTOP_CONFIG_KEY_DEFAULT_GROUP);
if (config->default_group < -1
|| config->default_group >=
xkl_engine_get_max_num_groups (config->engine))
config->default_group = -1;
xkl_debug (150, "default_group: %d\n", config->default_group);
}
void
gkbd_desktop_config_save (GkbdDesktopConfig * config)
{
g_settings_delay (config->settings);
g_settings_set_boolean (config->settings,
GKBD_DESKTOP_CONFIG_KEY_GROUP_PER_WINDOW,
config->group_per_app);
g_settings_set_boolean (config->settings,
GKBD_DESKTOP_CONFIG_KEY_HANDLE_INDICATORS,
config->handle_indicators);
g_settings_set_boolean (config->settings,
GKBD_DESKTOP_CONFIG_KEY_LAYOUT_NAMES_AS_GROUP_NAMES,
config->layout_names_as_group_names);
g_settings_set_boolean (config->settings,
GKBD_DESKTOP_CONFIG_KEY_LOAD_EXTRA_ITEMS,
config->load_extra_items);
g_settings_set_int (config->settings,
GKBD_DESKTOP_CONFIG_KEY_DEFAULT_GROUP,
config->default_group);
g_settings_apply (config->settings);
}
gboolean
gkbd_desktop_config_activate (GkbdDesktopConfig * config)
{
gboolean rv = TRUE;
xkl_engine_set_group_per_toplevel_window (config->engine,
config->group_per_app);
xkl_engine_set_indicators_handling (config->engine,
config->handle_indicators);
xkl_engine_set_default_group (config->engine,
config->default_group);
return rv;
}
void
gkbd_desktop_config_lock_next_group (GkbdDesktopConfig * config)
{
int group = xkl_engine_get_next_group (config->engine);
xkl_engine_lock_group (config->engine, group);
}
void
gkbd_desktop_config_lock_prev_group (GkbdDesktopConfig * config)
{
int group = xkl_engine_get_prev_group (config->engine);
xkl_engine_lock_group (config->engine, group);
}
void
gkbd_desktop_config_restore_group (GkbdDesktopConfig * config)
{
int group = xkl_engine_get_current_window_group (config->engine);
xkl_engine_lock_group (config->engine, group);
}
/**
* gkbd_desktop_config_start_listen:
* @func: (scope notified): a function to call when settings are changed
*/
void
gkbd_desktop_config_start_listen (GkbdDesktopConfig * config,
GCallback func, gpointer user_data)
{
config->config_listener_id =
g_signal_connect (config->settings, "changed", func,
user_data);
}
void
gkbd_desktop_config_stop_listen (GkbdDesktopConfig * config)
{
g_signal_handler_disconnect (config->settings,
config->config_listener_id);
config->config_listener_id = 0;
}
gboolean
gkbd_desktop_config_load_group_descriptions (GkbdDesktopConfig
* config,
XklConfigRegistry *
registry,
const gchar **
layout_ids,
const gchar **
variant_ids,
gchar ***
short_group_names,
gchar *** full_group_names)
{
gchar **sld, **lld, **svd, **lvd;
gchar **psld, **plld, **plvd;
gchar **psgn, **pfgn, **psvd;
gint total_descriptions;
if (!gkbd_desktop_config_get_lv_descriptions
(config, registry, layout_ids, variant_ids, &sld, &lld, &svd,
&lvd)) {
return False;
}
total_descriptions = g_strv_length (sld);
*short_group_names = psgn =
g_new0 (gchar *, total_descriptions + 1);
*full_group_names = pfgn =
g_new0 (gchar *, total_descriptions + 1);
plld = lld;
psld = sld;
plvd = lvd;
psvd = svd;
while (plld != NULL && *plld != NULL) {
*psgn++ = g_strdup ((*psvd[0] == '\0') ? *psld : *psvd);
*pfgn++ =
g_strdup (gkbd_keyboard_config_format_full_description
(*plld, *plvd));
psld++, psvd++;
plld++, plvd++;
}
g_strfreev (sld);
g_strfreev (lld);
g_strfreev (svd);
g_strfreev (lvd);
return True;
}