#ifdef HAVE_CONFIG_H
# include "config.h"
+#include "claws-features.h"
#endif
#ifdef USE_ENCHANT
static void gtkaspell_checkers_error_message (gchar *message);
/* Callbacks */
+static gboolean key_press_cb (GtkWidget *text_view,
+ GdkEventKey *event,
+ GtkAspell *gtkaspell);
static void entry_insert_cb (GtkTextBuffer *textbuf,
GtkTextIter *iter,
gchar *newtext,
static void reset_theword_data (GtkAspell *gtkaspell);
static void free_checkers (gpointer elt,
gpointer data);
-static gint find_gtkaspeller (gconstpointer aa,
- gconstpointer bb);
static void destroy_menu(GtkWidget *widget, gpointer user_data);
if (!alt_gtkaspeller) {
gtkaspell_checkers_error_message(
g_strdup_printf(_("Couldn't initialize %s speller."), dictionary));
+ gtkaspeller_delete(gtkaspeller);
g_free(gtkaspell);
return NULL;
}
allocate_color(gtkaspell, misspelled_color);
+ g_signal_connect(G_OBJECT(gtktext), "key_press_event",
+ G_CALLBACK(key_press_cb), gtkaspell);
g_signal_connect_after(G_OBJECT(buffer), "insert-text",
G_CALLBACK(entry_insert_cb), gtkaspell);
g_signal_connect_after(G_OBJECT(buffer), "delete-range",
{
GtkTextView *gtktext = gtkaspell->gtktext;
+ g_signal_handlers_disconnect_by_func(G_OBJECT(gtktext),
+ G_CALLBACK(key_press_cb),
+ gtkaspell);
g_signal_handlers_disconnect_by_func(G_OBJECT(gtktext),
G_CALLBACK(entry_insert_cb),
gtkaspell);
gtkaspell->dict_changed_cb(gtkaspell->menu_changed_data);
}
+static gboolean key_press_cb (GtkWidget *text_view,
+ GdkEventKey *event,
+ GtkAspell *gtkaspell)
+{
+ gint pos;
+
+ cm_return_val_if_fail(gtkaspell->gtkaspeller->speller, FALSE);
+
+ if (!gtkaspell->check_while_typing)
+ return FALSE;
+
+ switch (event->keyval) {
+ case GDK_KEY_Home:
+ case GDK_KEY_Left:
+ case GDK_KEY_Up:
+ case GDK_KEY_Right:
+ case GDK_KEY_Down:
+ case GDK_KEY_Page_Up:
+ case GDK_KEY_Page_Down:
+ case GDK_KEY_End:
+ case GDK_KEY_Begin:
+ pos = get_textview_buffer_offset(GTK_TEXT_VIEW(text_view));
+ if (pos > 0)
+ check_at(gtkaspell, pos - 1);
+ else
+ check_at(gtkaspell, pos);
+ break;
+ default:
+ break;
+ }
+
+ return FALSE;
+}
+
static void entry_insert_cb(GtkTextBuffer *textbuf,
GtkTextIter *iter,
gchar *newtext,
GtkAspell *gtkaspell)
{
int origpos;
- gint start, end;
+ gint start;
cm_return_if_fail(gtkaspell->gtkaspeller->speller);
return;
start = gtk_text_iter_get_offset(startiter);
- end = gtk_text_iter_get_offset(enditer);
origpos = get_textview_buffer_offset(gtkaspell->gtktext);
if (start) {
check_at(gtkaspell, start - 1);
/* Checker creation */
static GtkAspeller *gtkaspeller_new(Dictionary *dictionary)
{
- GSList *exist;
GtkAspeller *gtkaspeller = NULL;
GtkAspeller *tmp;
Dictionary *dict;
tmp = g_new0(GtkAspeller, 1);
tmp->dictionary = dict;
- exist = g_slist_find_custom(gtkaspellcheckers->checkers, tmp,
- find_gtkaspeller);
-
g_free(tmp);
if ((gtkaspeller = gtkaspeller_real_new(dict)) != NULL) {
{
gint start, end;
char buf[GTKASPELLWORDSIZE];
- GtkTextView *gtktext;
cm_return_val_if_fail(from_pos >= 0, FALSE);
- gtktext = gtkaspell->gtktext;
-
if (!get_word_from_pos(gtkaspell, from_pos, buf, sizeof(buf),
&start, &end))
return FALSE;
set_point_continue(gtkaspell);
}
+void gtkaspell_block_check(GtkAspell *gtkaspell)
+{
+ GtkTextView *gtktext;
+
+ if (gtkaspell == NULL)
+ return;
+
+ gtktext = gtkaspell->gtktext;
+ g_signal_handlers_block_by_func(G_OBJECT(gtktext),
+ G_CALLBACK(key_press_cb),
+ gtkaspell);
+ g_signal_handlers_block_by_func(G_OBJECT(gtktext),
+ G_CALLBACK(entry_insert_cb),
+ gtkaspell);
+ g_signal_handlers_block_by_func(G_OBJECT(gtktext),
+ G_CALLBACK(entry_delete_cb),
+ gtkaspell);
+}
+
+void gtkaspell_unblock_check(GtkAspell *gtkaspell)
+{
+ GtkTextView *gtktext;
+
+ if (gtkaspell == NULL)
+ return;
+
+ gtktext = gtkaspell->gtktext;
+ g_signal_handlers_unblock_by_func(G_OBJECT(gtktext),
+ G_CALLBACK(key_press_cb),
+ gtkaspell);
+ g_signal_handlers_unblock_by_func(G_OBJECT(gtktext),
+ G_CALLBACK(entry_insert_cb),
+ gtkaspell);
+ g_signal_handlers_unblock_by_func(G_OBJECT(gtktext),
+ G_CALLBACK(entry_delete_cb),
+ gtkaspell);
+}
+
static void replace_real_word(GtkAspell *gtkaspell, const gchar *newword)
{
- int oldlen, newlen, wordlen;
+ int oldlen, newlen;
gint origpos;
gint pos;
GtkTextView *gtktext;
origpos = gtkaspell->orig_pos;
pos = origpos;
oldlen = gtkaspell->end_pos - gtkaspell->start_pos;
- wordlen = strlen(gtkaspell->theword);
newlen = strlen(newword); /* FIXME: multybyte characters? */
- g_signal_handlers_block_by_func(G_OBJECT(gtktext),
- G_CALLBACK(entry_insert_cb),
- gtkaspell);
- g_signal_handlers_block_by_func(G_OBJECT(gtktext),
- G_CALLBACK(entry_delete_cb),
- gtkaspell);
+ gtkaspell_block_check(gtkaspell);
gtk_text_buffer_get_iter_at_offset(textbuf, &startiter,
gtkaspell->start_pos);
g_signal_emit_by_name(G_OBJECT(textbuf), "insert-text",
&startiter, newword, newlen, gtkaspell);
- g_signal_handlers_unblock_by_func(G_OBJECT(gtktext),
- G_CALLBACK(entry_insert_cb),
- gtkaspell);
- g_signal_handlers_unblock_by_func(G_OBJECT(gtktext),
- G_CALLBACK(entry_delete_cb),
- gtkaspell);
+ gtkaspell_unblock_check(gtkaspell);
/* Put the point and the position where we clicked with the mouse
* It seems to be a hack, as I must thaw,freeze,thaw the widget
/* Accept this word for this session */
static void add_word_to_session_cb(GtkWidget *w, gpointer data)
{
- GtkTextView *gtktext;
GtkAspell *gtkaspell = (GtkAspell *) data;
- gtktext = gtkaspell->gtktext;
-
enchant_dict_add_to_session(gtkaspell->gtkaspeller->speller, gtkaspell->theword, strlen(gtkaspell->theword));
GdkEventKey *event,
GtkAspell *gtkaspell)
{
- if (event && event->keyval == GDK_Escape) {
+ if (event && event->keyval == GDK_KEY_Escape) {
gtk_widget_destroy(widget);
return TRUE;
- } else if (event && event->keyval == GDK_Return) {
+ } else if (event && event->keyval == GDK_KEY_Return) {
replace_with_supplied_word_cb(widget, gtkaspell);
return TRUE;
}
static PangoFontDescription *font_desc;
GtkWidget *dialog;
GtkWidget *label;
- GtkWidget *w_hbox;
GtkWidget *hbox;
GtkWidget *vbox;
GtkWidget *entry;
thelabel = g_strdup_printf(_("<span weight=\"bold\" "
"size=\"larger\">Replace \"%s\" with: </span>"),
utf8buf);
- /* for title label */
- w_hbox = gtk_hbox_new(FALSE, 0);
icon = gtk_image_new_from_stock(GTK_STOCK_DIALOG_QUESTION,
GTK_ICON_SIZE_DIALOG);
gtk_box_pack_start(GTK_BOX(vbox), label, FALSE, FALSE, 0);
gtk_widget_show(label);
- hbox = gtk_hbox_new(TRUE, 0);
-
gtkut_stock_button_set_create(&confirm_area,
&cancel_button, GTK_STOCK_CANCEL,
&ok_button, GTK_STOCK_OK,
GdkEventKey *event,
GtkAspell *gtkaspell)
{
- if (event && (isascii(event->keyval) || event->keyval == GDK_Return)) {
+ if (event && (isascii(event->keyval) || event->keyval == GDK_KEY_Return)) {
gtk_accel_groups_activate(
G_OBJECT(gtkaspell->parent_window),
event->keyval, event->state);
- } else if (event && event->keyval == GDK_Escape) {
+ } else if (event && event->keyval == GDK_KEY_Escape) {
destroy_menu(NULL, gtkaspell);
}
return FALSE;
}
+/* Create a paged submenu with choice of available dictionaries */
+static GtkWidget *make_dictionary_list_submenu(GtkAspell *gtkaspell)
+{
+ GtkWidget *menu, *curmenu, *moremenu, *item;
+ int count = 2;
+ Dictionary *dict;
+ GSList *tmp;
+
+ /* Dict list */
+ if (gtkaspellcheckers->dictionary_list == NULL)
+ gtkaspell_get_dictionary_list(FALSE);
+
+ menu = gtk_menu_new();
+ curmenu = menu;
+
+ item = gtk_menu_item_new_with_label(_("Change to..."));
+ gtk_menu_shell_append(GTK_MENU_SHELL(menu), item);
+
+ item = gtk_separator_menu_item_new();
+ gtk_menu_shell_append(GTK_MENU_SHELL(menu), item);
+
+ for (tmp = gtkaspellcheckers->dictionary_list; tmp != NULL;
+ tmp = g_slist_next(tmp)) {
+ if (count == MENUCOUNT) {
+
+ moremenu = gtk_menu_new();
+ item = gtk_menu_item_new_with_label(_("More..."));
+ gtk_menu_item_set_submenu(GTK_MENU_ITEM(item),
+ moremenu);
+
+ gtk_menu_shell_append(GTK_MENU_SHELL(curmenu), item);
+ curmenu = moremenu;
+ count = 0;
+ }
+ dict = (Dictionary *) tmp->data;
+ item = gtk_check_menu_item_new_with_label(dict->fullname);
+ g_object_set_data(G_OBJECT(item), "dict_name",
+ dict->dictname);
+ if (strcmp2(dict->fullname,
+ gtkaspell->gtkaspeller->dictionary->fullname))
+ gtk_check_menu_item_set_active(GTK_CHECK_MENU_ITEM(item), FALSE);
+ else {
+ gtk_check_menu_item_set_active(GTK_CHECK_MENU_ITEM(item), TRUE);
+ gtk_widget_set_sensitive(GTK_WIDGET(item),
+ FALSE);
+ }
+ g_signal_connect(G_OBJECT(item), "activate",
+ G_CALLBACK(change_dict_cb),
+ gtkaspell);
+ gtk_menu_shell_append(GTK_MENU_SHELL(curmenu), item);
+
+ count++;
+ }
+
+ gtk_widget_show_all(menu);
+ return menu;
+}
+
/* make_sug_menu() - Add menus to accept this word for this session
* and to add it to personal dictionary
*/
static GSList *make_sug_menu(GtkAspell *gtkaspell)
{
- GtkWidget *item;
+ GtkWidget *item, *submenu;
char *caption;
- GtkTextView *gtktext;
GtkAccelGroup *accel;
GList *l = gtkaspell->suggestions_list;
gchar *utf8buf;
GSList *list = NULL;
- gtktext = gtkaspell->gtktext;
if (l == NULL)
return NULL;
}
utf8buf = g_strdup(l->data);
- caption = g_strdup_printf(_("\"%s\" unknown in %s"),
+ caption = g_strdup_printf(_("\"%s\" unknown in dictionary '%s'"),
utf8buf,
gtkaspell->gtkaspeller->dictionary->dictname);
item = gtk_menu_item_new_with_label(caption);
+ submenu = make_dictionary_list_submenu(gtkaspell);
+ gtk_menu_item_set_submenu(GTK_MENU_ITEM(item), submenu);
g_free(utf8buf);
gtk_widget_show(item);
list = g_slist_append(list, item);
g_signal_connect(G_OBJECT(item), "activate",
G_CALLBACK(add_word_to_session_cb),
gtkaspell);
- gtk_widget_add_accelerator(item, "activate", accel, GDK_space,
+ gtk_widget_add_accelerator(item, "activate", accel, GDK_KEY_space,
GDK_CONTROL_MASK,
GTK_ACCEL_LOCKED | GTK_ACCEL_VISIBLE);
g_signal_connect(G_OBJECT(item), "activate",
G_CALLBACK(add_word_to_personal_cb),
gtkaspell);
- gtk_widget_add_accelerator(item, "activate", accel, GDK_Return,
+ gtk_widget_add_accelerator(item, "activate", accel, GDK_KEY_Return,
GDK_CONTROL_MASK,
GTK_ACCEL_LOCKED | GTK_ACCEL_VISIBLE);
g_signal_connect(G_OBJECT(item), "activate",
G_CALLBACK(replace_with_create_dialog_cb),
gtkaspell);
- gtk_widget_add_accelerator(item, "activate", accel, GDK_R, 0,
+ gtk_widget_add_accelerator(item, "activate", accel, GDK_KEY_R, 0,
GTK_ACCEL_LOCKED | GTK_ACCEL_VISIBLE);
- gtk_widget_add_accelerator(item, "activate", accel, GDK_R,
+ gtk_widget_add_accelerator(item, "activate", accel, GDK_KEY_R,
GDK_CONTROL_MASK,
GTK_ACCEL_LOCKED);
g_signal_connect(G_OBJECT(item), "activate",
G_CALLBACK(check_with_alternate_cb),
gtkaspell);
- gtk_widget_add_accelerator(item, "activate", accel, GDK_X, 0,
+ gtk_widget_add_accelerator(item, "activate", accel, GDK_KEY_X, 0,
GTK_ACCEL_LOCKED | GTK_ACCEL_VISIBLE);
- gtk_widget_add_accelerator(item, "activate", accel, GDK_X,
+ gtk_widget_add_accelerator(item, "activate", accel, GDK_KEY_X,
GDK_CONTROL_MASK,
GTK_ACCEL_LOCKED);
}
if (curmenu == NULL && count < MENUCOUNT) {
gtk_widget_add_accelerator(item, "activate",
accel,
- GDK_A + count, 0,
+ GDK_KEY_A + count, 0,
GTK_ACCEL_LOCKED |
GTK_ACCEL_VISIBLE);
gtk_widget_add_accelerator(item, "activate",
accel,
- GDK_A + count,
+ GDK_KEY_A + count,
GDK_CONTROL_MASK,
GTK_ACCEL_LOCKED);
}
item = gtk_menu_item_new_with_label(dictname);
gtk_misc_set_alignment(GTK_MISC(gtk_bin_get_child(GTK_BIN((item)))), 0.5, 0.5);
g_free(dictname);
+ submenu = make_dictionary_list_submenu(gtkaspell);
+ gtk_menu_item_set_submenu(GTK_MENU_ITEM(item), submenu);
gtk_widget_show(item);
list = g_slist_append(list, item);
gtk_widget_show(item);
list = g_slist_append(list, item);
- item = gtk_menu_item_new();
- gtk_widget_show(item);
- list = g_slist_append(list, item);
-
- submenu = gtk_menu_new();
- item = gtk_menu_item_new_with_label(_("Change dictionary"));
- gtk_menu_item_set_submenu(GTK_MENU_ITEM(item),submenu);
- gtk_widget_show(item);
- list = g_slist_append(list, item);
-
- /* Dict list */
- if (gtkaspellcheckers->dictionary_list == NULL)
- gtkaspell_get_dictionary_list(FALSE);
- {
- GtkWidget * curmenu = submenu;
- int count = 0;
- Dictionary *dict;
- GSList *tmp;
- tmp = gtkaspellcheckers->dictionary_list;
-
- for (tmp = gtkaspellcheckers->dictionary_list; tmp != NULL;
- tmp = g_slist_next(tmp)) {
- if (count == MENUCOUNT) {
- GtkWidget *newmenu;
-
- newmenu = gtk_menu_new();
- item = gtk_menu_item_new_with_label(_("More..."));
- gtk_menu_item_set_submenu(GTK_MENU_ITEM(item),
- newmenu);
-
- gtk_menu_shell_append(GTK_MENU_SHELL(curmenu), item);
- gtk_widget_show(item);
- curmenu = newmenu;
- count = 0;
- }
- dict = (Dictionary *) tmp->data;
- item = gtk_check_menu_item_new_with_label(dict->dictname);
- g_object_set_data(G_OBJECT(item), "dict_name",
- dict->fullname);
- if (strcmp2(dict->fullname,
- gtkaspell->gtkaspeller->dictionary->fullname))
- gtk_check_menu_item_set_active(GTK_CHECK_MENU_ITEM(item), FALSE);
- else {
- gtk_check_menu_item_set_active(GTK_CHECK_MENU_ITEM(item), TRUE);
- gtk_widget_set_sensitive(GTK_WIDGET(item),
- FALSE);
- }
- g_signal_connect(G_OBJECT(item), "activate",
- G_CALLBACK(change_dict_cb),
- gtkaspell);
- gtk_widget_show(item);
- gtk_menu_shell_append(GTK_MENU_SHELL(curmenu), item);
-
- count++;
- }
- }
return list;
}
static void set_point_continue(GtkAspell *gtkaspell)
{
- GtkTextView *gtktext;
-
- gtktext = gtkaspell->gtktext;
-
gtkaspell->ctx.set_position(gtkaspell->ctx.data, gtkaspell->orig_pos);
if (gtkaspell->continue_check)
gtkaspeller_real_delete(gtkaspeller);
}
-static gint find_gtkaspeller(gconstpointer aa, gconstpointer bb)
-{
- Dictionary *a = ((GtkAspeller *) aa)->dictionary;
- Dictionary *b = ((GtkAspeller *) bb)->dictionary;
-
- if (a && b && a->fullname && b->fullname)
- return strcmp(a->fullname, b->fullname);
-
- return 1;
-}
-
gchar *gtkaspell_get_default_dictionary(GtkAspell *gtkaspell)
{
if (gtkaspell && gtkaspell->gtkaspeller &&