Mercurial > pidgin
annotate finch/libgnt/gntentry.c @ 21262:aee0d7fef769
transpose-chars action for the entry boxes.
author | Sadrul Habib Chowdhury <imadil@gmail.com> |
---|---|
date | Fri, 26 Oct 2007 07:27:00 +0000 |
parents | 9187d331aebe |
children | 1f59065c606a |
rev | line source |
---|---|
17928
8410511f4dbb
applied changes from 016401bd409e6229fae0ab1e80d9fef9365511b3
Eric Polino <aluink@pidgin.im>
parents:
16899
diff
changeset
|
1 /** |
8410511f4dbb
applied changes from 016401bd409e6229fae0ab1e80d9fef9365511b3
Eric Polino <aluink@pidgin.im>
parents:
16899
diff
changeset
|
2 * GNT - The GLib Ncurses Toolkit |
8410511f4dbb
applied changes from 016401bd409e6229fae0ab1e80d9fef9365511b3
Eric Polino <aluink@pidgin.im>
parents:
16899
diff
changeset
|
3 * |
8410511f4dbb
applied changes from 016401bd409e6229fae0ab1e80d9fef9365511b3
Eric Polino <aluink@pidgin.im>
parents:
16899
diff
changeset
|
4 * GNT is the legal property of its developers, whose names are too numerous |
8410511f4dbb
applied changes from 016401bd409e6229fae0ab1e80d9fef9365511b3
Eric Polino <aluink@pidgin.im>
parents:
16899
diff
changeset
|
5 * to list here. Please refer to the COPYRIGHT file distributed with this |
8410511f4dbb
applied changes from 016401bd409e6229fae0ab1e80d9fef9365511b3
Eric Polino <aluink@pidgin.im>
parents:
16899
diff
changeset
|
6 * source distribution. |
8410511f4dbb
applied changes from 016401bd409e6229fae0ab1e80d9fef9365511b3
Eric Polino <aluink@pidgin.im>
parents:
16899
diff
changeset
|
7 * |
8410511f4dbb
applied changes from 016401bd409e6229fae0ab1e80d9fef9365511b3
Eric Polino <aluink@pidgin.im>
parents:
16899
diff
changeset
|
8 * This library is free software; you can redistribute it and/or modify |
8410511f4dbb
applied changes from 016401bd409e6229fae0ab1e80d9fef9365511b3
Eric Polino <aluink@pidgin.im>
parents:
16899
diff
changeset
|
9 * it under the terms of the GNU General Public License as published by |
8410511f4dbb
applied changes from 016401bd409e6229fae0ab1e80d9fef9365511b3
Eric Polino <aluink@pidgin.im>
parents:
16899
diff
changeset
|
10 * the Free Software Foundation; either version 2 of the License, or |
8410511f4dbb
applied changes from 016401bd409e6229fae0ab1e80d9fef9365511b3
Eric Polino <aluink@pidgin.im>
parents:
16899
diff
changeset
|
11 * (at your option) any later version. |
8410511f4dbb
applied changes from 016401bd409e6229fae0ab1e80d9fef9365511b3
Eric Polino <aluink@pidgin.im>
parents:
16899
diff
changeset
|
12 * |
8410511f4dbb
applied changes from 016401bd409e6229fae0ab1e80d9fef9365511b3
Eric Polino <aluink@pidgin.im>
parents:
16899
diff
changeset
|
13 * This program is distributed in the hope that it will be useful, |
8410511f4dbb
applied changes from 016401bd409e6229fae0ab1e80d9fef9365511b3
Eric Polino <aluink@pidgin.im>
parents:
16899
diff
changeset
|
14 * but WITHOUT ANY WARRANTY; without even the implied warranty of |
8410511f4dbb
applied changes from 016401bd409e6229fae0ab1e80d9fef9365511b3
Eric Polino <aluink@pidgin.im>
parents:
16899
diff
changeset
|
15 * MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the |
8410511f4dbb
applied changes from 016401bd409e6229fae0ab1e80d9fef9365511b3
Eric Polino <aluink@pidgin.im>
parents:
16899
diff
changeset
|
16 * GNU General Public License for more details. |
8410511f4dbb
applied changes from 016401bd409e6229fae0ab1e80d9fef9365511b3
Eric Polino <aluink@pidgin.im>
parents:
16899
diff
changeset
|
17 * |
8410511f4dbb
applied changes from 016401bd409e6229fae0ab1e80d9fef9365511b3
Eric Polino <aluink@pidgin.im>
parents:
16899
diff
changeset
|
18 * You should have received a copy of the GNU General Public License |
8410511f4dbb
applied changes from 016401bd409e6229fae0ab1e80d9fef9365511b3
Eric Polino <aluink@pidgin.im>
parents:
16899
diff
changeset
|
19 * along with this program; if not, write to the Free Software |
19681
44b4e8bd759b
The FSF changed its address a while ago; our files were out of date.
John Bailey <rekkanoryo@rekkanoryo.org>
parents:
18873
diff
changeset
|
20 * Foundation, Inc., 51 Franklin Street, Fifth Floor, Boston, MA 02111-1301 USA |
17928
8410511f4dbb
applied changes from 016401bd409e6229fae0ab1e80d9fef9365511b3
Eric Polino <aluink@pidgin.im>
parents:
16899
diff
changeset
|
21 */ |
8410511f4dbb
applied changes from 016401bd409e6229fae0ab1e80d9fef9365511b3
Eric Polino <aluink@pidgin.im>
parents:
16899
diff
changeset
|
22 |
15817 | 23 #include <ctype.h> |
24 #include <string.h> | |
25 | |
26 #include "gntbox.h" | |
27 #include "gntentry.h" | |
18382
aa60f5a89286
A 'completion' signal to emit whenever user accepts a completion suggest.
Sadrul Habib Chowdhury <imadil@gmail.com>
parents:
18346
diff
changeset
|
28 #include "gntmarshal.h" |
15817 | 29 #include "gntstyle.h" |
30 #include "gnttree.h" | |
31 #include "gntutils.h" | |
32 | |
33 enum | |
34 { | |
35 SIG_TEXT_CHANGED, | |
18382
aa60f5a89286
A 'completion' signal to emit whenever user accepts a completion suggest.
Sadrul Habib Chowdhury <imadil@gmail.com>
parents:
18346
diff
changeset
|
36 SIG_COMPLETION, |
15817 | 37 SIGS, |
38 }; | |
39 static guint signals[SIGS] = { 0 }; | |
40 | |
41 static GntWidgetClass *parent_class = NULL; | |
42 | |
15959
efbced3f38ac
Update the tab completion a little bit. The binding for suggest-show will perform suggest-next if the suggest-dropdown is already showing. If there's just one suggestion, then complete with that suggestion.
Sadrul Habib Chowdhury <imadil@gmail.com>
parents:
15817
diff
changeset
|
43 static gboolean gnt_entry_key_pressed(GntWidget *widget, const char *text); |
15817 | 44 static void gnt_entry_set_text_internal(GntEntry *entry, const char *text); |
45 | |
46 static void | |
47 destroy_suggest(GntEntry *entry) | |
48 { | |
49 if (entry->ddown) | |
50 { | |
51 gnt_widget_destroy(entry->ddown->parent); | |
52 entry->ddown = NULL; | |
53 } | |
54 } | |
55 | |
56 static char * | |
57 get_beginning_of_word(GntEntry *entry) | |
58 { | |
59 char *s = entry->cursor; | |
60 while (s > entry->start) | |
61 { | |
62 char *t = g_utf8_find_prev_char(entry->start, s); | |
63 if (isspace(*t)) | |
64 break; | |
65 s = t; | |
66 } | |
67 return s; | |
68 } | |
69 | |
70 static gboolean | |
16889
c31328dba5c2
Fix some ickyness in the tab-completion. Now, if there's only one suggest word, then the first tab will just complete the suggestion. If there's only one suggest word, and it's already completed, then tab will take focus to the next widget. If there is a dropdown, then you can select a suggest word by pressing tabs to move to it, then either space or enter to accept it.
Sadrul Habib Chowdhury <imadil@gmail.com>
parents:
15959
diff
changeset
|
71 complete_suggest(GntEntry *entry, const char *text) |
c31328dba5c2
Fix some ickyness in the tab-completion. Now, if there's only one suggest word, then the first tab will just complete the suggestion. If there's only one suggest word, and it's already completed, then tab will take focus to the next widget. If there is a dropdown, then you can select a suggest word by pressing tabs to move to it, then either space or enter to accept it.
Sadrul Habib Chowdhury <imadil@gmail.com>
parents:
15959
diff
changeset
|
72 { |
c31328dba5c2
Fix some ickyness in the tab-completion. Now, if there's only one suggest word, then the first tab will just complete the suggestion. If there's only one suggest word, and it's already completed, then tab will take focus to the next widget. If there is a dropdown, then you can select a suggest word by pressing tabs to move to it, then either space or enter to accept it.
Sadrul Habib Chowdhury <imadil@gmail.com>
parents:
15959
diff
changeset
|
73 gboolean changed = FALSE; |
18382
aa60f5a89286
A 'completion' signal to emit whenever user accepts a completion suggest.
Sadrul Habib Chowdhury <imadil@gmail.com>
parents:
18346
diff
changeset
|
74 int offstart = 0, offend = 0; |
aa60f5a89286
A 'completion' signal to emit whenever user accepts a completion suggest.
Sadrul Habib Chowdhury <imadil@gmail.com>
parents:
18346
diff
changeset
|
75 |
16889
c31328dba5c2
Fix some ickyness in the tab-completion. Now, if there's only one suggest word, then the first tab will just complete the suggestion. If there's only one suggest word, and it's already completed, then tab will take focus to the next widget. If there is a dropdown, then you can select a suggest word by pressing tabs to move to it, then either space or enter to accept it.
Sadrul Habib Chowdhury <imadil@gmail.com>
parents:
15959
diff
changeset
|
76 if (entry->word) { |
c31328dba5c2
Fix some ickyness in the tab-completion. Now, if there's only one suggest word, then the first tab will just complete the suggestion. If there's only one suggest word, and it's already completed, then tab will take focus to the next widget. If there is a dropdown, then you can select a suggest word by pressing tabs to move to it, then either space or enter to accept it.
Sadrul Habib Chowdhury <imadil@gmail.com>
parents:
15959
diff
changeset
|
77 char *s = get_beginning_of_word(entry); |
c31328dba5c2
Fix some ickyness in the tab-completion. Now, if there's only one suggest word, then the first tab will just complete the suggestion. If there's only one suggest word, and it's already completed, then tab will take focus to the next widget. If there is a dropdown, then you can select a suggest word by pressing tabs to move to it, then either space or enter to accept it.
Sadrul Habib Chowdhury <imadil@gmail.com>
parents:
15959
diff
changeset
|
78 const char *iter = text; |
18382
aa60f5a89286
A 'completion' signal to emit whenever user accepts a completion suggest.
Sadrul Habib Chowdhury <imadil@gmail.com>
parents:
18346
diff
changeset
|
79 offstart = g_utf8_pointer_to_offset(entry->start, s); |
16889
c31328dba5c2
Fix some ickyness in the tab-completion. Now, if there's only one suggest word, then the first tab will just complete the suggestion. If there's only one suggest word, and it's already completed, then tab will take focus to the next widget. If there is a dropdown, then you can select a suggest word by pressing tabs to move to it, then either space or enter to accept it.
Sadrul Habib Chowdhury <imadil@gmail.com>
parents:
15959
diff
changeset
|
80 while (*iter && toupper(*s) == toupper(*iter)) { |
c31328dba5c2
Fix some ickyness in the tab-completion. Now, if there's only one suggest word, then the first tab will just complete the suggestion. If there's only one suggest word, and it's already completed, then tab will take focus to the next widget. If there is a dropdown, then you can select a suggest word by pressing tabs to move to it, then either space or enter to accept it.
Sadrul Habib Chowdhury <imadil@gmail.com>
parents:
15959
diff
changeset
|
81 if (*s != *iter) |
c31328dba5c2
Fix some ickyness in the tab-completion. Now, if there's only one suggest word, then the first tab will just complete the suggestion. If there's only one suggest word, and it's already completed, then tab will take focus to the next widget. If there is a dropdown, then you can select a suggest word by pressing tabs to move to it, then either space or enter to accept it.
Sadrul Habib Chowdhury <imadil@gmail.com>
parents:
15959
diff
changeset
|
82 changed = TRUE; |
c31328dba5c2
Fix some ickyness in the tab-completion. Now, if there's only one suggest word, then the first tab will just complete the suggestion. If there's only one suggest word, and it's already completed, then tab will take focus to the next widget. If there is a dropdown, then you can select a suggest word by pressing tabs to move to it, then either space or enter to accept it.
Sadrul Habib Chowdhury <imadil@gmail.com>
parents:
15959
diff
changeset
|
83 *s++ = *iter++; |
c31328dba5c2
Fix some ickyness in the tab-completion. Now, if there's only one suggest word, then the first tab will just complete the suggestion. If there's only one suggest word, and it's already completed, then tab will take focus to the next widget. If there is a dropdown, then you can select a suggest word by pressing tabs to move to it, then either space or enter to accept it.
Sadrul Habib Chowdhury <imadil@gmail.com>
parents:
15959
diff
changeset
|
84 } |
c31328dba5c2
Fix some ickyness in the tab-completion. Now, if there's only one suggest word, then the first tab will just complete the suggestion. If there's only one suggest word, and it's already completed, then tab will take focus to the next widget. If there is a dropdown, then you can select a suggest word by pressing tabs to move to it, then either space or enter to accept it.
Sadrul Habib Chowdhury <imadil@gmail.com>
parents:
15959
diff
changeset
|
85 if (*iter) { |
c31328dba5c2
Fix some ickyness in the tab-completion. Now, if there's only one suggest word, then the first tab will just complete the suggestion. If there's only one suggest word, and it's already completed, then tab will take focus to the next widget. If there is a dropdown, then you can select a suggest word by pressing tabs to move to it, then either space or enter to accept it.
Sadrul Habib Chowdhury <imadil@gmail.com>
parents:
15959
diff
changeset
|
86 gnt_entry_key_pressed(GNT_WIDGET(entry), iter); |
c31328dba5c2
Fix some ickyness in the tab-completion. Now, if there's only one suggest word, then the first tab will just complete the suggestion. If there's only one suggest word, and it's already completed, then tab will take focus to the next widget. If there is a dropdown, then you can select a suggest word by pressing tabs to move to it, then either space or enter to accept it.
Sadrul Habib Chowdhury <imadil@gmail.com>
parents:
15959
diff
changeset
|
87 changed = TRUE; |
c31328dba5c2
Fix some ickyness in the tab-completion. Now, if there's only one suggest word, then the first tab will just complete the suggestion. If there's only one suggest word, and it's already completed, then tab will take focus to the next widget. If there is a dropdown, then you can select a suggest word by pressing tabs to move to it, then either space or enter to accept it.
Sadrul Habib Chowdhury <imadil@gmail.com>
parents:
15959
diff
changeset
|
88 } |
18382
aa60f5a89286
A 'completion' signal to emit whenever user accepts a completion suggest.
Sadrul Habib Chowdhury <imadil@gmail.com>
parents:
18346
diff
changeset
|
89 offend = g_utf8_pointer_to_offset(entry->start, entry->cursor); |
16889
c31328dba5c2
Fix some ickyness in the tab-completion. Now, if there's only one suggest word, then the first tab will just complete the suggestion. If there's only one suggest word, and it's already completed, then tab will take focus to the next widget. If there is a dropdown, then you can select a suggest word by pressing tabs to move to it, then either space or enter to accept it.
Sadrul Habib Chowdhury <imadil@gmail.com>
parents:
15959
diff
changeset
|
90 } else { |
18382
aa60f5a89286
A 'completion' signal to emit whenever user accepts a completion suggest.
Sadrul Habib Chowdhury <imadil@gmail.com>
parents:
18346
diff
changeset
|
91 offstart = 0; |
16889
c31328dba5c2
Fix some ickyness in the tab-completion. Now, if there's only one suggest word, then the first tab will just complete the suggestion. If there's only one suggest word, and it's already completed, then tab will take focus to the next widget. If there is a dropdown, then you can select a suggest word by pressing tabs to move to it, then either space or enter to accept it.
Sadrul Habib Chowdhury <imadil@gmail.com>
parents:
15959
diff
changeset
|
92 gnt_entry_set_text_internal(entry, text); |
c31328dba5c2
Fix some ickyness in the tab-completion. Now, if there's only one suggest word, then the first tab will just complete the suggestion. If there's only one suggest word, and it's already completed, then tab will take focus to the next widget. If there is a dropdown, then you can select a suggest word by pressing tabs to move to it, then either space or enter to accept it.
Sadrul Habib Chowdhury <imadil@gmail.com>
parents:
15959
diff
changeset
|
93 changed = TRUE; |
18382
aa60f5a89286
A 'completion' signal to emit whenever user accepts a completion suggest.
Sadrul Habib Chowdhury <imadil@gmail.com>
parents:
18346
diff
changeset
|
94 offend = g_utf8_strlen(text, -1); |
16889
c31328dba5c2
Fix some ickyness in the tab-completion. Now, if there's only one suggest word, then the first tab will just complete the suggestion. If there's only one suggest word, and it's already completed, then tab will take focus to the next widget. If there is a dropdown, then you can select a suggest word by pressing tabs to move to it, then either space or enter to accept it.
Sadrul Habib Chowdhury <imadil@gmail.com>
parents:
15959
diff
changeset
|
95 } |
18382
aa60f5a89286
A 'completion' signal to emit whenever user accepts a completion suggest.
Sadrul Habib Chowdhury <imadil@gmail.com>
parents:
18346
diff
changeset
|
96 |
aa60f5a89286
A 'completion' signal to emit whenever user accepts a completion suggest.
Sadrul Habib Chowdhury <imadil@gmail.com>
parents:
18346
diff
changeset
|
97 if (changed) |
aa60f5a89286
A 'completion' signal to emit whenever user accepts a completion suggest.
Sadrul Habib Chowdhury <imadil@gmail.com>
parents:
18346
diff
changeset
|
98 g_signal_emit(G_OBJECT(entry), signals[SIG_COMPLETION], 0, |
aa60f5a89286
A 'completion' signal to emit whenever user accepts a completion suggest.
Sadrul Habib Chowdhury <imadil@gmail.com>
parents:
18346
diff
changeset
|
99 entry->start + offstart, entry->start + offend); |
16889
c31328dba5c2
Fix some ickyness in the tab-completion. Now, if there's only one suggest word, then the first tab will just complete the suggestion. If there's only one suggest word, and it's already completed, then tab will take focus to the next widget. If there is a dropdown, then you can select a suggest word by pressing tabs to move to it, then either space or enter to accept it.
Sadrul Habib Chowdhury <imadil@gmail.com>
parents:
15959
diff
changeset
|
100 return changed; |
c31328dba5c2
Fix some ickyness in the tab-completion. Now, if there's only one suggest word, then the first tab will just complete the suggestion. If there's only one suggest word, and it's already completed, then tab will take focus to the next widget. If there is a dropdown, then you can select a suggest word by pressing tabs to move to it, then either space or enter to accept it.
Sadrul Habib Chowdhury <imadil@gmail.com>
parents:
15959
diff
changeset
|
101 } |
c31328dba5c2
Fix some ickyness in the tab-completion. Now, if there's only one suggest word, then the first tab will just complete the suggestion. If there's only one suggest word, and it's already completed, then tab will take focus to the next widget. If there is a dropdown, then you can select a suggest word by pressing tabs to move to it, then either space or enter to accept it.
Sadrul Habib Chowdhury <imadil@gmail.com>
parents:
15959
diff
changeset
|
102 |
20088
470feb3084a4
Tab-complete as much as possible when there are multiple suggests.
Sadrul Habib Chowdhury <imadil@gmail.com>
parents:
19681
diff
changeset
|
103 static int |
470feb3084a4
Tab-complete as much as possible when there are multiple suggests.
Sadrul Habib Chowdhury <imadil@gmail.com>
parents:
19681
diff
changeset
|
104 max_common_prefix(const char *s, const char *t) |
470feb3084a4
Tab-complete as much as possible when there are multiple suggests.
Sadrul Habib Chowdhury <imadil@gmail.com>
parents:
19681
diff
changeset
|
105 { |
470feb3084a4
Tab-complete as much as possible when there are multiple suggests.
Sadrul Habib Chowdhury <imadil@gmail.com>
parents:
19681
diff
changeset
|
106 const char *f = s; |
470feb3084a4
Tab-complete as much as possible when there are multiple suggests.
Sadrul Habib Chowdhury <imadil@gmail.com>
parents:
19681
diff
changeset
|
107 while (*f && *t && *f == *t++) |
470feb3084a4
Tab-complete as much as possible when there are multiple suggests.
Sadrul Habib Chowdhury <imadil@gmail.com>
parents:
19681
diff
changeset
|
108 f++; |
470feb3084a4
Tab-complete as much as possible when there are multiple suggests.
Sadrul Habib Chowdhury <imadil@gmail.com>
parents:
19681
diff
changeset
|
109 return f - s; |
470feb3084a4
Tab-complete as much as possible when there are multiple suggests.
Sadrul Habib Chowdhury <imadil@gmail.com>
parents:
19681
diff
changeset
|
110 } |
470feb3084a4
Tab-complete as much as possible when there are multiple suggests.
Sadrul Habib Chowdhury <imadil@gmail.com>
parents:
19681
diff
changeset
|
111 |
16889
c31328dba5c2
Fix some ickyness in the tab-completion. Now, if there's only one suggest word, then the first tab will just complete the suggestion. If there's only one suggest word, and it's already completed, then tab will take focus to the next widget. If there is a dropdown, then you can select a suggest word by pressing tabs to move to it, then either space or enter to accept it.
Sadrul Habib Chowdhury <imadil@gmail.com>
parents:
15959
diff
changeset
|
112 static gboolean |
15817 | 113 show_suggest_dropdown(GntEntry *entry) |
114 { | |
115 char *suggest = NULL; | |
116 int len; | |
117 int offset = 0, x, y; | |
118 int count = 0; | |
119 GList *iter; | |
16889
c31328dba5c2
Fix some ickyness in the tab-completion. Now, if there's only one suggest word, then the first tab will just complete the suggestion. If there's only one suggest word, and it's already completed, then tab will take focus to the next widget. If there is a dropdown, then you can select a suggest word by pressing tabs to move to it, then either space or enter to accept it.
Sadrul Habib Chowdhury <imadil@gmail.com>
parents:
15959
diff
changeset
|
120 const char *text = NULL; |
16899
6502a3846264
Fix tab-completion.
Sadrul Habib Chowdhury <imadil@gmail.com>
parents:
16889
diff
changeset
|
121 const char *sgst = NULL; |
20088
470feb3084a4
Tab-complete as much as possible when there are multiple suggests.
Sadrul Habib Chowdhury <imadil@gmail.com>
parents:
19681
diff
changeset
|
122 int max = -1; |
15817 | 123 |
124 if (entry->word) | |
125 { | |
126 char *s = get_beginning_of_word(entry); | |
127 suggest = g_strndup(s, entry->cursor - s); | |
128 if (entry->scroll < s) | |
129 offset = gnt_util_onscreen_width(entry->scroll, s); | |
130 } | |
131 else | |
132 suggest = g_strdup(entry->start); | |
133 len = strlen(suggest); /* Don't need to use the utf8-function here */ | |
20088
470feb3084a4
Tab-complete as much as possible when there are multiple suggests.
Sadrul Habib Chowdhury <imadil@gmail.com>
parents:
19681
diff
changeset
|
134 |
15817 | 135 if (entry->ddown == NULL) |
136 { | |
137 GntWidget *box = gnt_vbox_new(FALSE); | |
138 entry->ddown = gnt_tree_new(); | |
139 gnt_tree_set_compare_func(GNT_TREE(entry->ddown), (GCompareFunc)g_utf8_collate); | |
140 gnt_box_add_widget(GNT_BOX(box), entry->ddown); | |
141 | |
142 GNT_WIDGET_SET_FLAGS(box, GNT_WIDGET_TRANSIENT); | |
143 | |
144 gnt_widget_get_position(GNT_WIDGET(entry), &x, &y); | |
145 x += offset; | |
146 y++; | |
147 if (y + 10 >= getmaxy(stdscr)) | |
148 y -= 11; | |
149 gnt_widget_set_position(box, x, y); | |
150 } | |
151 else | |
152 gnt_tree_remove_all(GNT_TREE(entry->ddown)); | |
153 | |
154 for (count = 0, iter = entry->suggests; iter; iter = iter->next) | |
155 { | |
16889
c31328dba5c2
Fix some ickyness in the tab-completion. Now, if there's only one suggest word, then the first tab will just complete the suggestion. If there's only one suggest word, and it's already completed, then tab will take focus to the next widget. If there is a dropdown, then you can select a suggest word by pressing tabs to move to it, then either space or enter to accept it.
Sadrul Habib Chowdhury <imadil@gmail.com>
parents:
15959
diff
changeset
|
156 text = iter->data; |
15817 | 157 if (g_ascii_strncasecmp(suggest, text, len) == 0 && strlen(text) >= len) |
158 { | |
159 gnt_tree_add_row_after(GNT_TREE(entry->ddown), (gpointer)text, | |
160 gnt_tree_create_row(GNT_TREE(entry->ddown), text), | |
161 NULL, NULL); | |
162 count++; | |
20088
470feb3084a4
Tab-complete as much as possible when there are multiple suggests.
Sadrul Habib Chowdhury <imadil@gmail.com>
parents:
19681
diff
changeset
|
163 if (max == -1) |
470feb3084a4
Tab-complete as much as possible when there are multiple suggests.
Sadrul Habib Chowdhury <imadil@gmail.com>
parents:
19681
diff
changeset
|
164 max = strlen(text) - len; |
470feb3084a4
Tab-complete as much as possible when there are multiple suggests.
Sadrul Habib Chowdhury <imadil@gmail.com>
parents:
19681
diff
changeset
|
165 else if (max) |
470feb3084a4
Tab-complete as much as possible when there are multiple suggests.
Sadrul Habib Chowdhury <imadil@gmail.com>
parents:
19681
diff
changeset
|
166 max = MIN(max, max_common_prefix(sgst + len, text + len)); |
16899
6502a3846264
Fix tab-completion.
Sadrul Habib Chowdhury <imadil@gmail.com>
parents:
16889
diff
changeset
|
167 sgst = text; |
15817 | 168 } |
169 } | |
170 g_free(suggest); | |
171 | |
16889
c31328dba5c2
Fix some ickyness in the tab-completion. Now, if there's only one suggest word, then the first tab will just complete the suggestion. If there's only one suggest word, and it's already completed, then tab will take focus to the next widget. If there is a dropdown, then you can select a suggest word by pressing tabs to move to it, then either space or enter to accept it.
Sadrul Habib Chowdhury <imadil@gmail.com>
parents:
15959
diff
changeset
|
172 if (count == 0) { |
15817 | 173 destroy_suggest(entry); |
174 return FALSE; | |
16889
c31328dba5c2
Fix some ickyness in the tab-completion. Now, if there's only one suggest word, then the first tab will just complete the suggestion. If there's only one suggest word, and it's already completed, then tab will take focus to the next widget. If there is a dropdown, then you can select a suggest word by pressing tabs to move to it, then either space or enter to accept it.
Sadrul Habib Chowdhury <imadil@gmail.com>
parents:
15959
diff
changeset
|
175 } else if (count == 1) { |
c31328dba5c2
Fix some ickyness in the tab-completion. Now, if there's only one suggest word, then the first tab will just complete the suggestion. If there's only one suggest word, and it's already completed, then tab will take focus to the next widget. If there is a dropdown, then you can select a suggest word by pressing tabs to move to it, then either space or enter to accept it.
Sadrul Habib Chowdhury <imadil@gmail.com>
parents:
15959
diff
changeset
|
176 destroy_suggest(entry); |
16899
6502a3846264
Fix tab-completion.
Sadrul Habib Chowdhury <imadil@gmail.com>
parents:
16889
diff
changeset
|
177 return complete_suggest(entry, sgst); |
16889
c31328dba5c2
Fix some ickyness in the tab-completion. Now, if there's only one suggest word, then the first tab will just complete the suggestion. If there's only one suggest word, and it's already completed, then tab will take focus to the next widget. If there is a dropdown, then you can select a suggest word by pressing tabs to move to it, then either space or enter to accept it.
Sadrul Habib Chowdhury <imadil@gmail.com>
parents:
15959
diff
changeset
|
178 } else { |
20088
470feb3084a4
Tab-complete as much as possible when there are multiple suggests.
Sadrul Habib Chowdhury <imadil@gmail.com>
parents:
19681
diff
changeset
|
179 if (max > 0) { |
470feb3084a4
Tab-complete as much as possible when there are multiple suggests.
Sadrul Habib Chowdhury <imadil@gmail.com>
parents:
19681
diff
changeset
|
180 GntWidget *ddown = entry->ddown; |
470feb3084a4
Tab-complete as much as possible when there are multiple suggests.
Sadrul Habib Chowdhury <imadil@gmail.com>
parents:
19681
diff
changeset
|
181 char *match = g_strndup(sgst + len, max); |
470feb3084a4
Tab-complete as much as possible when there are multiple suggests.
Sadrul Habib Chowdhury <imadil@gmail.com>
parents:
19681
diff
changeset
|
182 entry->ddown = NULL; |
470feb3084a4
Tab-complete as much as possible when there are multiple suggests.
Sadrul Habib Chowdhury <imadil@gmail.com>
parents:
19681
diff
changeset
|
183 gnt_entry_key_pressed(GNT_WIDGET(entry), match); |
470feb3084a4
Tab-complete as much as possible when there are multiple suggests.
Sadrul Habib Chowdhury <imadil@gmail.com>
parents:
19681
diff
changeset
|
184 g_free(match); |
470feb3084a4
Tab-complete as much as possible when there are multiple suggests.
Sadrul Habib Chowdhury <imadil@gmail.com>
parents:
19681
diff
changeset
|
185 if (entry->ddown) |
470feb3084a4
Tab-complete as much as possible when there are multiple suggests.
Sadrul Habib Chowdhury <imadil@gmail.com>
parents:
19681
diff
changeset
|
186 gnt_widget_destroy(ddown); |
470feb3084a4
Tab-complete as much as possible when there are multiple suggests.
Sadrul Habib Chowdhury <imadil@gmail.com>
parents:
19681
diff
changeset
|
187 else |
470feb3084a4
Tab-complete as much as possible when there are multiple suggests.
Sadrul Habib Chowdhury <imadil@gmail.com>
parents:
19681
diff
changeset
|
188 entry->ddown = ddown; |
470feb3084a4
Tab-complete as much as possible when there are multiple suggests.
Sadrul Habib Chowdhury <imadil@gmail.com>
parents:
19681
diff
changeset
|
189 } |
16889
c31328dba5c2
Fix some ickyness in the tab-completion. Now, if there's only one suggest word, then the first tab will just complete the suggestion. If there's only one suggest word, and it's already completed, then tab will take focus to the next widget. If there is a dropdown, then you can select a suggest word by pressing tabs to move to it, then either space or enter to accept it.
Sadrul Habib Chowdhury <imadil@gmail.com>
parents:
15959
diff
changeset
|
190 gnt_widget_draw(entry->ddown->parent); |
15817 | 191 } |
192 | |
193 return TRUE; | |
194 } | |
195 | |
196 static void | |
197 gnt_entry_draw(GntWidget *widget) | |
198 { | |
199 GntEntry *entry = GNT_ENTRY(widget); | |
200 int stop; | |
201 gboolean focus; | |
202 | |
203 if ((focus = gnt_widget_has_focus(widget))) | |
21250
9187d331aebe
Add gnt_color_pair, which will replace color codes with 'appropriate' text
Sadrul Habib Chowdhury <imadil@gmail.com>
parents:
20088
diff
changeset
|
204 wbkgdset(widget->window, '\0' | gnt_color_pair(GNT_COLOR_TEXT_NORMAL)); |
15817 | 205 else |
21250
9187d331aebe
Add gnt_color_pair, which will replace color codes with 'appropriate' text
Sadrul Habib Chowdhury <imadil@gmail.com>
parents:
20088
diff
changeset
|
206 wbkgdset(widget->window, '\0' | gnt_color_pair(GNT_COLOR_HIGHLIGHT_D)); |
15817 | 207 |
208 if (entry->masked) | |
209 { | |
210 mvwhline(widget->window, 0, 0, gnt_ascii_only() ? '*' : ACS_BULLET, | |
211 g_utf8_pointer_to_offset(entry->scroll, entry->end)); | |
212 } | |
213 else | |
214 mvwprintw(widget->window, 0, 0, "%s", entry->scroll); | |
215 | |
216 stop = gnt_util_onscreen_width(entry->scroll, entry->end); | |
217 if (stop < widget->priv.width) | |
18346
72a52cff76f3
Draw the password entries correctly.
Sadrul Habib Chowdhury <imadil@gmail.com>
parents:
17928
diff
changeset
|
218 mvwhline(widget->window, 0, stop, ENTRY_CHAR, widget->priv.width - stop); |
15817 | 219 |
220 if (focus) | |
221 mvwchgat(widget->window, 0, gnt_util_onscreen_width(entry->scroll, entry->cursor), | |
222 1, A_REVERSE, GNT_COLOR_TEXT_NORMAL, NULL); | |
223 | |
224 GNTDEBUG; | |
225 } | |
226 | |
227 static void | |
228 gnt_entry_size_request(GntWidget *widget) | |
229 { | |
230 if (!GNT_WIDGET_IS_FLAG_SET(widget, GNT_WIDGET_MAPPED)) | |
231 { | |
232 widget->priv.height = 1; | |
233 widget->priv.width = 20; | |
234 } | |
235 } | |
236 | |
237 static void | |
238 gnt_entry_map(GntWidget *widget) | |
239 { | |
240 if (widget->priv.width == 0 || widget->priv.height == 0) | |
241 gnt_widget_size_request(widget); | |
242 GNTDEBUG; | |
243 } | |
244 | |
245 static void | |
246 entry_redraw(GntWidget *widget) | |
247 { | |
248 gnt_entry_draw(widget); | |
249 gnt_widget_queue_update(widget); | |
250 } | |
251 | |
252 static void | |
253 entry_text_changed(GntEntry *entry) | |
254 { | |
255 g_signal_emit(entry, signals[SIG_TEXT_CHANGED], 0); | |
256 } | |
257 | |
258 static gboolean | |
259 move_back(GntBindable *bind, GList *null) | |
260 { | |
261 GntEntry *entry = GNT_ENTRY(bind); | |
262 if (entry->cursor <= entry->start) | |
263 return FALSE; | |
264 entry->cursor = g_utf8_find_prev_char(entry->start, entry->cursor); | |
265 if (entry->cursor < entry->scroll) | |
266 entry->scroll = entry->cursor; | |
267 entry_redraw(GNT_WIDGET(entry)); | |
268 return TRUE; | |
269 } | |
270 | |
271 static gboolean | |
272 move_forward(GntBindable *bind, GList *list) | |
273 { | |
274 GntEntry *entry = GNT_ENTRY(bind); | |
275 if (entry->cursor >= entry->end) | |
276 return FALSE; | |
277 entry->cursor = g_utf8_find_next_char(entry->cursor, NULL); | |
278 while (gnt_util_onscreen_width(entry->scroll, entry->cursor) >= GNT_WIDGET(entry)->priv.width) | |
279 entry->scroll = g_utf8_find_next_char(entry->scroll, NULL); | |
280 entry_redraw(GNT_WIDGET(entry)); | |
281 return TRUE; | |
282 } | |
283 | |
284 static gboolean | |
285 backspace(GntBindable *bind, GList *null) | |
286 { | |
287 int len; | |
288 GntEntry *entry = GNT_ENTRY(bind); | |
289 | |
290 if (entry->cursor <= entry->start) | |
291 return TRUE; | |
292 | |
293 len = entry->cursor - g_utf8_find_prev_char(entry->start, entry->cursor); | |
294 entry->cursor -= len; | |
295 memmove(entry->cursor, entry->cursor + len, entry->end - entry->cursor); | |
296 entry->end -= len; | |
297 | |
298 if (entry->scroll > entry->start) | |
299 entry->scroll = g_utf8_find_prev_char(entry->start, entry->scroll); | |
300 | |
301 entry_redraw(GNT_WIDGET(entry)); | |
302 if (entry->ddown) | |
303 show_suggest_dropdown(entry); | |
304 entry_text_changed(entry); | |
305 return TRUE; | |
306 } | |
307 | |
308 static gboolean | |
309 delkey(GntBindable *bind, GList *null) | |
310 { | |
311 int len; | |
312 GntEntry *entry = GNT_ENTRY(bind); | |
313 | |
314 if (entry->cursor >= entry->end) | |
315 return FALSE; | |
316 | |
317 len = g_utf8_find_next_char(entry->cursor, NULL) - entry->cursor; | |
318 memmove(entry->cursor, entry->cursor + len, entry->end - entry->cursor - len + 1); | |
319 entry->end -= len; | |
320 entry_redraw(GNT_WIDGET(entry)); | |
321 | |
322 if (entry->ddown) | |
323 show_suggest_dropdown(entry); | |
324 entry_text_changed(entry); | |
325 return TRUE; | |
326 } | |
327 | |
328 static gboolean | |
329 move_start(GntBindable *bind, GList *null) | |
330 { | |
331 GntEntry *entry = GNT_ENTRY(bind); | |
332 entry->scroll = entry->cursor = entry->start; | |
333 entry_redraw(GNT_WIDGET(entry)); | |
334 return TRUE; | |
335 } | |
336 | |
337 static gboolean | |
338 move_end(GntBindable *bind, GList *null) | |
339 { | |
340 GntEntry *entry = GNT_ENTRY(bind); | |
341 entry->cursor = entry->end; | |
342 /* This should be better than this */ | |
343 while (gnt_util_onscreen_width(entry->scroll, entry->cursor) >= GNT_WIDGET(entry)->priv.width) | |
344 entry->scroll = g_utf8_find_next_char(entry->scroll, NULL); | |
345 entry_redraw(GNT_WIDGET(entry)); | |
346 return TRUE; | |
347 } | |
348 | |
349 static gboolean | |
350 history_prev(GntBindable *bind, GList *null) | |
351 { | |
352 GntEntry *entry = GNT_ENTRY(bind); | |
353 if (entry->histlength && entry->history->prev) | |
354 { | |
355 entry->history = entry->history->prev; | |
356 gnt_entry_set_text_internal(entry, entry->history->data); | |
357 destroy_suggest(entry); | |
358 entry_text_changed(entry); | |
359 | |
360 return TRUE; | |
361 } | |
362 return FALSE; | |
363 } | |
364 | |
365 static gboolean | |
366 history_next(GntBindable *bind, GList *null) | |
367 { | |
368 GntEntry *entry = GNT_ENTRY(bind); | |
369 if (entry->histlength && entry->history->next) | |
370 { | |
371 if (entry->history->prev == NULL) | |
372 { | |
373 /* Save the current contents */ | |
374 char *text = g_strdup(gnt_entry_get_text(entry)); | |
375 g_free(entry->history->data); | |
376 entry->history->data = text; | |
377 } | |
378 | |
379 entry->history = entry->history->next; | |
380 gnt_entry_set_text_internal(entry, entry->history->data); | |
381 destroy_suggest(entry); | |
382 entry_text_changed(entry); | |
383 | |
384 return TRUE; | |
385 } | |
386 return FALSE; | |
387 } | |
388 | |
389 static gboolean | |
390 clipboard_paste(GntBindable *bind, GList *n) | |
391 { | |
392 GntEntry *entry = GNT_ENTRY(bind); | |
393 gchar *i, *text, *a, *all; | |
394 text = i = gnt_get_clipboard_string(); | |
395 while (*i != '\0') { | |
396 i = g_utf8_next_char(i); | |
397 if (*i == '\r' || *i == '\n') | |
398 *i = ' '; | |
399 } | |
400 a = g_strndup(entry->start, entry->cursor - entry->start); | |
401 all = g_strconcat(a, text, entry->cursor, NULL); | |
402 gnt_entry_set_text_internal(entry, all); | |
403 g_free(a); | |
404 g_free(text); | |
405 g_free(all); | |
406 return TRUE; | |
407 } | |
408 | |
409 static gboolean | |
410 suggest_show(GntBindable *bind, GList *null) | |
411 { | |
15959
efbced3f38ac
Update the tab completion a little bit. The binding for suggest-show will perform suggest-next if the suggest-dropdown is already showing. If there's just one suggestion, then complete with that suggestion.
Sadrul Habib Chowdhury <imadil@gmail.com>
parents:
15817
diff
changeset
|
412 GntEntry *entry = GNT_ENTRY(bind); |
efbced3f38ac
Update the tab completion a little bit. The binding for suggest-show will perform suggest-next if the suggest-dropdown is already showing. If there's just one suggestion, then complete with that suggestion.
Sadrul Habib Chowdhury <imadil@gmail.com>
parents:
15817
diff
changeset
|
413 if (entry->ddown) { |
16889
c31328dba5c2
Fix some ickyness in the tab-completion. Now, if there's only one suggest word, then the first tab will just complete the suggestion. If there's only one suggest word, and it's already completed, then tab will take focus to the next widget. If there is a dropdown, then you can select a suggest word by pressing tabs to move to it, then either space or enter to accept it.
Sadrul Habib Chowdhury <imadil@gmail.com>
parents:
15959
diff
changeset
|
414 gnt_bindable_perform_action_named(GNT_BINDABLE(entry->ddown), "move-down"); |
15959
efbced3f38ac
Update the tab completion a little bit. The binding for suggest-show will perform suggest-next if the suggest-dropdown is already showing. If there's just one suggestion, then complete with that suggestion.
Sadrul Habib Chowdhury <imadil@gmail.com>
parents:
15817
diff
changeset
|
415 return TRUE; |
efbced3f38ac
Update the tab completion a little bit. The binding for suggest-show will perform suggest-next if the suggest-dropdown is already showing. If there's just one suggestion, then complete with that suggestion.
Sadrul Habib Chowdhury <imadil@gmail.com>
parents:
15817
diff
changeset
|
416 } |
efbced3f38ac
Update the tab completion a little bit. The binding for suggest-show will perform suggest-next if the suggest-dropdown is already showing. If there's just one suggestion, then complete with that suggestion.
Sadrul Habib Chowdhury <imadil@gmail.com>
parents:
15817
diff
changeset
|
417 return show_suggest_dropdown(entry); |
15817 | 418 } |
419 | |
420 static gboolean | |
421 suggest_next(GntBindable *bind, GList *null) | |
422 { | |
423 GntEntry *entry = GNT_ENTRY(bind); | |
424 if (entry->ddown) { | |
425 gnt_bindable_perform_action_named(GNT_BINDABLE(entry->ddown), "move-down", NULL); | |
426 return TRUE; | |
427 } | |
428 return FALSE; | |
429 } | |
430 | |
431 static gboolean | |
432 suggest_prev(GntBindable *bind, GList *null) | |
433 { | |
434 GntEntry *entry = GNT_ENTRY(bind); | |
435 if (entry->ddown) { | |
436 gnt_bindable_perform_action_named(GNT_BINDABLE(entry->ddown), "move-up", NULL); | |
437 return TRUE; | |
438 } | |
439 return FALSE; | |
440 } | |
441 | |
442 static gboolean | |
443 del_to_home(GntBindable *bind, GList *null) | |
444 { | |
445 GntEntry *entry = GNT_ENTRY(bind); | |
446 if (entry->cursor <= entry->start) | |
447 return TRUE; | |
448 memmove(entry->start, entry->cursor, entry->end - entry->cursor); | |
449 entry->end -= (entry->cursor - entry->start); | |
450 entry->cursor = entry->scroll = entry->start; | |
451 memset(entry->end, '\0', entry->buffer - (entry->end - entry->start)); | |
452 entry_redraw(GNT_WIDGET(bind)); | |
453 entry_text_changed(entry); | |
454 return TRUE; | |
455 } | |
456 | |
457 static gboolean | |
458 del_to_end(GntBindable *bind, GList *null) | |
459 { | |
460 GntEntry *entry = GNT_ENTRY(bind); | |
461 if (entry->end <= entry->cursor) | |
462 return TRUE; | |
463 entry->end = entry->cursor; | |
464 memset(entry->end, '\0', entry->buffer - (entry->end - entry->start)); | |
465 entry_redraw(GNT_WIDGET(bind)); | |
466 entry_text_changed(entry); | |
467 return TRUE; | |
468 } | |
469 | |
470 #define SAME(a,b) ((g_unichar_isalpha(a) && g_unichar_isalpha(b)) || \ | |
471 (g_unichar_isdigit(a) && g_unichar_isdigit(b)) || \ | |
472 (g_unichar_isspace(a) && g_unichar_isspace(b)) || \ | |
473 (g_unichar_iswide(a) && g_unichar_iswide(b))) | |
474 | |
475 static const char * | |
476 begin_word(const char *text, const char *begin) | |
477 { | |
478 gunichar ch = 0; | |
479 while (text > begin && (!*text || g_unichar_isspace(g_utf8_get_char(text)))) | |
480 text = g_utf8_find_prev_char(begin, text); | |
481 ch = g_utf8_get_char(text); | |
482 while ((text = g_utf8_find_prev_char(begin, text)) >= begin) { | |
483 gunichar cur = g_utf8_get_char(text); | |
484 if (!SAME(ch, cur)) | |
485 break; | |
486 } | |
487 | |
488 return (text ? g_utf8_find_next_char(text, NULL) : begin); | |
489 } | |
490 | |
491 static const char * | |
492 next_begin_word(const char *text, const char *end) | |
493 { | |
494 gunichar ch = 0; | |
495 ch = g_utf8_get_char(text); | |
496 while ((text = g_utf8_find_next_char(text, end)) != NULL && text <= end) { | |
497 gunichar cur = g_utf8_get_char(text); | |
498 if (!SAME(ch, cur)) | |
499 break; | |
500 } | |
501 | |
502 while (text && text < end && g_unichar_isspace(g_utf8_get_char(text))) | |
503 text = g_utf8_find_next_char(text, end); | |
504 return (text ? text : end); | |
505 } | |
506 | |
507 #undef SAME | |
508 static gboolean | |
509 move_back_word(GntBindable *bind, GList *null) | |
510 { | |
511 GntEntry *entry = GNT_ENTRY(bind); | |
512 const char *iter = g_utf8_find_prev_char(entry->start, entry->cursor); | |
513 | |
514 if (iter < entry->start) | |
515 return TRUE; | |
516 iter = begin_word(iter, entry->start); | |
517 entry->cursor = (char*)iter; | |
518 if (entry->cursor < entry->scroll) | |
519 entry->scroll = entry->cursor; | |
520 entry_redraw(GNT_WIDGET(bind)); | |
521 return TRUE; | |
522 } | |
523 | |
524 static gboolean | |
525 del_prev_word(GntBindable *bind, GList *null) | |
526 { | |
527 GntWidget *widget = GNT_WIDGET(bind); | |
528 GntEntry *entry = GNT_ENTRY(bind); | |
529 char *iter = g_utf8_find_prev_char(entry->start, entry->cursor); | |
530 int count; | |
531 | |
532 if (iter < entry->start) | |
533 return TRUE; | |
534 iter = (char*)begin_word(iter, entry->start); | |
535 count = entry->cursor - iter; | |
536 memmove(iter, entry->cursor, entry->end - entry->cursor); | |
537 entry->end -= count; | |
538 entry->cursor = iter; | |
539 if (entry->cursor <= entry->scroll) { | |
540 entry->scroll = entry->cursor - widget->priv.width + 2; | |
541 if (entry->scroll < entry->start) | |
542 entry->scroll = entry->start; | |
543 } | |
544 memset(entry->end, '\0', entry->buffer - (entry->end - entry->start)); | |
545 entry_redraw(widget); | |
546 entry_text_changed(entry); | |
547 | |
548 return TRUE; | |
549 } | |
550 | |
551 static gboolean | |
552 move_forward_word(GntBindable *bind, GList *list) | |
553 { | |
554 GntEntry *entry = GNT_ENTRY(bind); | |
555 GntWidget *widget = GNT_WIDGET(bind); | |
556 entry->cursor = (char *)next_begin_word(entry->cursor, entry->end); | |
557 while (gnt_util_onscreen_width(entry->scroll, entry->cursor) >= widget->priv.width) { | |
558 entry->scroll = g_utf8_find_next_char(entry->scroll, NULL); | |
559 } | |
560 entry_redraw(widget); | |
561 return TRUE; | |
562 } | |
563 | |
564 static gboolean | |
565 delete_forward_word(GntBindable *bind, GList *list) | |
566 { | |
567 GntEntry *entry = GNT_ENTRY(bind); | |
568 GntWidget *widget = GNT_WIDGET(bind); | |
569 char *iter = (char *)next_begin_word(entry->cursor, entry->end); | |
570 int len = entry->end - iter + 1; | |
571 if (len <= 0) | |
572 return TRUE; | |
573 memmove(entry->cursor, iter, len); | |
574 len = iter - entry->cursor; | |
575 entry->end -= len; | |
576 memset(entry->end, '\0', len); | |
577 entry_redraw(widget); | |
578 entry_text_changed(entry); | |
579 return TRUE; | |
580 } | |
581 | |
582 static gboolean | |
21262
aee0d7fef769
transpose-chars action for the entry boxes.
Sadrul Habib Chowdhury <imadil@gmail.com>
parents:
21250
diff
changeset
|
583 transpose_chars(GntBindable *bind, GList *null) |
aee0d7fef769
transpose-chars action for the entry boxes.
Sadrul Habib Chowdhury <imadil@gmail.com>
parents:
21250
diff
changeset
|
584 { |
aee0d7fef769
transpose-chars action for the entry boxes.
Sadrul Habib Chowdhury <imadil@gmail.com>
parents:
21250
diff
changeset
|
585 GntEntry *entry = GNT_ENTRY(bind); |
aee0d7fef769
transpose-chars action for the entry boxes.
Sadrul Habib Chowdhury <imadil@gmail.com>
parents:
21250
diff
changeset
|
586 char *current, *prev; |
aee0d7fef769
transpose-chars action for the entry boxes.
Sadrul Habib Chowdhury <imadil@gmail.com>
parents:
21250
diff
changeset
|
587 char hold[8]; /* that's right */ |
aee0d7fef769
transpose-chars action for the entry boxes.
Sadrul Habib Chowdhury <imadil@gmail.com>
parents:
21250
diff
changeset
|
588 |
aee0d7fef769
transpose-chars action for the entry boxes.
Sadrul Habib Chowdhury <imadil@gmail.com>
parents:
21250
diff
changeset
|
589 if (entry->cursor <= entry->start) |
aee0d7fef769
transpose-chars action for the entry boxes.
Sadrul Habib Chowdhury <imadil@gmail.com>
parents:
21250
diff
changeset
|
590 return FALSE; |
aee0d7fef769
transpose-chars action for the entry boxes.
Sadrul Habib Chowdhury <imadil@gmail.com>
parents:
21250
diff
changeset
|
591 |
aee0d7fef769
transpose-chars action for the entry boxes.
Sadrul Habib Chowdhury <imadil@gmail.com>
parents:
21250
diff
changeset
|
592 if (!*entry->cursor) |
aee0d7fef769
transpose-chars action for the entry boxes.
Sadrul Habib Chowdhury <imadil@gmail.com>
parents:
21250
diff
changeset
|
593 entry->cursor = g_utf8_find_prev_char(entry->start, entry->cursor); |
aee0d7fef769
transpose-chars action for the entry boxes.
Sadrul Habib Chowdhury <imadil@gmail.com>
parents:
21250
diff
changeset
|
594 |
aee0d7fef769
transpose-chars action for the entry boxes.
Sadrul Habib Chowdhury <imadil@gmail.com>
parents:
21250
diff
changeset
|
595 current = entry->cursor; |
aee0d7fef769
transpose-chars action for the entry boxes.
Sadrul Habib Chowdhury <imadil@gmail.com>
parents:
21250
diff
changeset
|
596 prev = g_utf8_find_prev_char(entry->start, entry->cursor); |
aee0d7fef769
transpose-chars action for the entry boxes.
Sadrul Habib Chowdhury <imadil@gmail.com>
parents:
21250
diff
changeset
|
597 move_forward(bind, null); |
aee0d7fef769
transpose-chars action for the entry boxes.
Sadrul Habib Chowdhury <imadil@gmail.com>
parents:
21250
diff
changeset
|
598 |
aee0d7fef769
transpose-chars action for the entry boxes.
Sadrul Habib Chowdhury <imadil@gmail.com>
parents:
21250
diff
changeset
|
599 /* Let's do this dance! */ |
aee0d7fef769
transpose-chars action for the entry boxes.
Sadrul Habib Chowdhury <imadil@gmail.com>
parents:
21250
diff
changeset
|
600 memcpy(hold, prev, current - prev); |
aee0d7fef769
transpose-chars action for the entry boxes.
Sadrul Habib Chowdhury <imadil@gmail.com>
parents:
21250
diff
changeset
|
601 memmove(prev, current, entry->cursor - current); |
aee0d7fef769
transpose-chars action for the entry boxes.
Sadrul Habib Chowdhury <imadil@gmail.com>
parents:
21250
diff
changeset
|
602 memcpy(prev + (entry->cursor - current), hold, current - prev); |
aee0d7fef769
transpose-chars action for the entry boxes.
Sadrul Habib Chowdhury <imadil@gmail.com>
parents:
21250
diff
changeset
|
603 |
aee0d7fef769
transpose-chars action for the entry boxes.
Sadrul Habib Chowdhury <imadil@gmail.com>
parents:
21250
diff
changeset
|
604 entry_redraw(GNT_WIDGET(entry)); |
aee0d7fef769
transpose-chars action for the entry boxes.
Sadrul Habib Chowdhury <imadil@gmail.com>
parents:
21250
diff
changeset
|
605 entry_text_changed(entry); |
aee0d7fef769
transpose-chars action for the entry boxes.
Sadrul Habib Chowdhury <imadil@gmail.com>
parents:
21250
diff
changeset
|
606 return TRUE; |
aee0d7fef769
transpose-chars action for the entry boxes.
Sadrul Habib Chowdhury <imadil@gmail.com>
parents:
21250
diff
changeset
|
607 } |
aee0d7fef769
transpose-chars action for the entry boxes.
Sadrul Habib Chowdhury <imadil@gmail.com>
parents:
21250
diff
changeset
|
608 |
aee0d7fef769
transpose-chars action for the entry boxes.
Sadrul Habib Chowdhury <imadil@gmail.com>
parents:
21250
diff
changeset
|
609 static gboolean |
15817 | 610 gnt_entry_key_pressed(GntWidget *widget, const char *text) |
611 { | |
612 GntEntry *entry = GNT_ENTRY(widget); | |
613 | |
614 if (text[0] == 27) | |
615 { | |
616 if (text[1] == 0) | |
617 { | |
618 destroy_suggest(entry); | |
619 return TRUE; | |
620 } | |
621 | |
622 return FALSE; | |
623 } | |
624 else | |
625 { | |
16889
c31328dba5c2
Fix some ickyness in the tab-completion. Now, if there's only one suggest word, then the first tab will just complete the suggestion. If there's only one suggest word, and it's already completed, then tab will take focus to the next widget. If there is a dropdown, then you can select a suggest word by pressing tabs to move to it, then either space or enter to accept it.
Sadrul Habib Chowdhury <imadil@gmail.com>
parents:
15959
diff
changeset
|
626 if ((text[0] == '\r' || text[0] == ' ') && entry->ddown) |
15817 | 627 { |
628 char *text = g_strdup(gnt_tree_get_selection_data(GNT_TREE(entry->ddown))); | |
629 destroy_suggest(entry); | |
16889
c31328dba5c2
Fix some ickyness in the tab-completion. Now, if there's only one suggest word, then the first tab will just complete the suggestion. If there's only one suggest word, and it's already completed, then tab will take focus to the next widget. If there is a dropdown, then you can select a suggest word by pressing tabs to move to it, then either space or enter to accept it.
Sadrul Habib Chowdhury <imadil@gmail.com>
parents:
15959
diff
changeset
|
630 complete_suggest(entry, text); |
15817 | 631 g_free(text); |
632 entry_text_changed(entry); | |
633 return TRUE; | |
634 } | |
635 | |
636 if (!iscntrl(text[0])) | |
637 { | |
638 const char *str, *next; | |
639 | |
640 for (str = text; *str; str = next) | |
641 { | |
642 int len; | |
643 next = g_utf8_find_next_char(str, NULL); | |
644 len = next - str; | |
645 | |
646 /* Valid input? */ | |
647 /* XXX: Is it necessary to use _unichar_ variants here? */ | |
648 if (ispunct(*str) && (entry->flag & GNT_ENTRY_FLAG_NO_PUNCT)) | |
649 continue; | |
650 if (isspace(*str) && (entry->flag & GNT_ENTRY_FLAG_NO_SPACE)) | |
651 continue; | |
652 if (isalpha(*str) && !(entry->flag & GNT_ENTRY_FLAG_ALPHA)) | |
653 continue; | |
654 if (isdigit(*str) && !(entry->flag & GNT_ENTRY_FLAG_INT)) | |
655 continue; | |
656 | |
657 /* Reached the max? */ | |
658 if (entry->max && g_utf8_pointer_to_offset(entry->start, entry->end) >= entry->max) | |
659 continue; | |
660 | |
661 if (entry->end + len - entry->start >= entry->buffer) | |
662 { | |
663 /* This will cause the buffer to grow */ | |
664 char *tmp = g_strdup(entry->start); | |
665 gnt_entry_set_text_internal(entry, tmp); | |
666 g_free(tmp); | |
667 } | |
668 | |
669 memmove(entry->cursor + len, entry->cursor, entry->end - entry->cursor + 1); | |
670 entry->end += len; | |
671 | |
672 while (str < next) | |
673 { | |
674 if (*str == '\r' || *str == '\n') | |
675 *entry->cursor = ' '; | |
676 else | |
677 *entry->cursor = *str; | |
678 entry->cursor++; | |
679 str++; | |
680 } | |
681 | |
682 while (gnt_util_onscreen_width(entry->scroll, entry->cursor) >= widget->priv.width) | |
683 entry->scroll = g_utf8_find_next_char(entry->scroll, NULL); | |
684 | |
685 if (entry->ddown) | |
686 show_suggest_dropdown(entry); | |
687 } | |
688 entry_redraw(widget); | |
689 entry_text_changed(entry); | |
690 return TRUE; | |
691 } | |
692 } | |
693 | |
694 return FALSE; | |
695 } | |
696 | |
697 static void | |
698 gnt_entry_destroy(GntWidget *widget) | |
699 { | |
700 GntEntry *entry = GNT_ENTRY(widget); | |
701 g_free(entry->start); | |
702 | |
703 if (entry->history) | |
704 { | |
705 entry->history = g_list_first(entry->history); | |
706 g_list_foreach(entry->history, (GFunc)g_free, NULL); | |
707 g_list_free(entry->history); | |
708 } | |
709 | |
710 if (entry->suggests) | |
711 { | |
712 g_list_foreach(entry->suggests, (GFunc)g_free, NULL); | |
713 g_list_free(entry->suggests); | |
714 } | |
715 | |
716 if (entry->ddown) | |
717 { | |
718 gnt_widget_destroy(entry->ddown->parent); | |
719 } | |
720 } | |
721 | |
722 static void | |
723 gnt_entry_lost_focus(GntWidget *widget) | |
724 { | |
725 GntEntry *entry = GNT_ENTRY(widget); | |
726 destroy_suggest(entry); | |
727 entry_redraw(widget); | |
728 } | |
729 | |
730 static void | |
731 gnt_entry_class_init(GntEntryClass *klass) | |
732 { | |
733 GntBindableClass *bindable = GNT_BINDABLE_CLASS(klass); | |
734 char s[2] = {erasechar(), 0}; | |
735 | |
736 parent_class = GNT_WIDGET_CLASS(klass); | |
737 parent_class->destroy = gnt_entry_destroy; | |
738 parent_class->draw = gnt_entry_draw; | |
739 parent_class->map = gnt_entry_map; | |
740 parent_class->size_request = gnt_entry_size_request; | |
741 parent_class->key_pressed = gnt_entry_key_pressed; | |
742 parent_class->lost_focus = gnt_entry_lost_focus; | |
743 | |
744 signals[SIG_TEXT_CHANGED] = | |
745 g_signal_new("text_changed", | |
746 G_TYPE_FROM_CLASS(klass), | |
747 G_SIGNAL_RUN_LAST, | |
748 G_STRUCT_OFFSET(GntEntryClass, text_changed), | |
749 NULL, NULL, | |
750 g_cclosure_marshal_VOID__VOID, | |
751 G_TYPE_NONE, 0); | |
752 | |
18382
aa60f5a89286
A 'completion' signal to emit whenever user accepts a completion suggest.
Sadrul Habib Chowdhury <imadil@gmail.com>
parents:
18346
diff
changeset
|
753 signals[SIG_COMPLETION] = |
aa60f5a89286
A 'completion' signal to emit whenever user accepts a completion suggest.
Sadrul Habib Chowdhury <imadil@gmail.com>
parents:
18346
diff
changeset
|
754 g_signal_new("completion", |
aa60f5a89286
A 'completion' signal to emit whenever user accepts a completion suggest.
Sadrul Habib Chowdhury <imadil@gmail.com>
parents:
18346
diff
changeset
|
755 G_TYPE_FROM_CLASS(klass), |
aa60f5a89286
A 'completion' signal to emit whenever user accepts a completion suggest.
Sadrul Habib Chowdhury <imadil@gmail.com>
parents:
18346
diff
changeset
|
756 G_SIGNAL_RUN_LAST, |
aa60f5a89286
A 'completion' signal to emit whenever user accepts a completion suggest.
Sadrul Habib Chowdhury <imadil@gmail.com>
parents:
18346
diff
changeset
|
757 0, NULL, NULL, |
aa60f5a89286
A 'completion' signal to emit whenever user accepts a completion suggest.
Sadrul Habib Chowdhury <imadil@gmail.com>
parents:
18346
diff
changeset
|
758 gnt_closure_marshal_VOID__POINTER_POINTER, |
aa60f5a89286
A 'completion' signal to emit whenever user accepts a completion suggest.
Sadrul Habib Chowdhury <imadil@gmail.com>
parents:
18346
diff
changeset
|
759 G_TYPE_NONE, 2, G_TYPE_POINTER, G_TYPE_POINTER); |
aa60f5a89286
A 'completion' signal to emit whenever user accepts a completion suggest.
Sadrul Habib Chowdhury <imadil@gmail.com>
parents:
18346
diff
changeset
|
760 |
15817 | 761 gnt_bindable_class_register_action(bindable, "cursor-home", move_start, |
762 GNT_KEY_CTRL_A, NULL); | |
763 gnt_bindable_register_binding(bindable, "cursor-home", GNT_KEY_HOME, NULL); | |
764 gnt_bindable_class_register_action(bindable, "cursor-end", move_end, | |
765 GNT_KEY_CTRL_E, NULL); | |
766 gnt_bindable_register_binding(bindable, "cursor-end", GNT_KEY_END, NULL); | |
767 gnt_bindable_class_register_action(bindable, "delete-prev", backspace, | |
768 GNT_KEY_BACKSPACE, NULL); | |
769 gnt_bindable_register_binding(bindable, "delete-prev", s, NULL); | |
770 gnt_bindable_register_binding(bindable, "delete-prev", GNT_KEY_CTRL_H, NULL); | |
771 gnt_bindable_class_register_action(bindable, "delete-next", delkey, | |
772 GNT_KEY_DEL, NULL); | |
773 gnt_bindable_register_binding(bindable, "delete-next", GNT_KEY_CTRL_D, NULL); | |
774 gnt_bindable_class_register_action(bindable, "delete-start", del_to_home, | |
775 GNT_KEY_CTRL_U, NULL); | |
776 gnt_bindable_class_register_action(bindable, "delete-end", del_to_end, | |
777 GNT_KEY_CTRL_K, NULL); | |
778 gnt_bindable_class_register_action(bindable, "delete-prev-word", del_prev_word, | |
779 GNT_KEY_CTRL_W, NULL); | |
780 gnt_bindable_class_register_action(bindable, "cursor-prev-word", move_back_word, | |
781 "\033" "b", NULL); | |
782 gnt_bindable_class_register_action(bindable, "cursor-prev", move_back, | |
783 GNT_KEY_LEFT, NULL); | |
784 gnt_bindable_register_binding(bindable, "cursor-prev", GNT_KEY_CTRL_B, NULL); | |
785 gnt_bindable_class_register_action(bindable, "cursor-next", move_forward, | |
786 GNT_KEY_RIGHT, NULL); | |
787 gnt_bindable_register_binding(bindable, "cursor-next", GNT_KEY_CTRL_F, NULL); | |
788 gnt_bindable_class_register_action(bindable, "cursor-next-word", move_forward_word, | |
789 "\033" "f", NULL); | |
790 gnt_bindable_class_register_action(bindable, "delete-next-word", delete_forward_word, | |
791 "\033" "d", NULL); | |
21262
aee0d7fef769
transpose-chars action for the entry boxes.
Sadrul Habib Chowdhury <imadil@gmail.com>
parents:
21250
diff
changeset
|
792 gnt_bindable_class_register_action(bindable, "transpose-chars", transpose_chars, |
aee0d7fef769
transpose-chars action for the entry boxes.
Sadrul Habib Chowdhury <imadil@gmail.com>
parents:
21250
diff
changeset
|
793 GNT_KEY_CTRL_T, NULL); |
15817 | 794 gnt_bindable_class_register_action(bindable, "suggest-show", suggest_show, |
795 "\t", NULL); | |
796 gnt_bindable_class_register_action(bindable, "suggest-next", suggest_next, | |
797 GNT_KEY_DOWN, NULL); | |
798 gnt_bindable_class_register_action(bindable, "suggest-prev", suggest_prev, | |
799 GNT_KEY_UP, NULL); | |
800 gnt_bindable_class_register_action(bindable, "history-prev", history_prev, | |
801 GNT_KEY_CTRL_DOWN, NULL); | |
802 gnt_bindable_class_register_action(bindable, "history-next", history_next, | |
803 GNT_KEY_CTRL_UP, NULL); | |
804 gnt_bindable_class_register_action(bindable, "clipboard-paste", clipboard_paste, | |
805 GNT_KEY_CTRL_V, NULL); | |
806 | |
807 gnt_style_read_actions(G_OBJECT_CLASS_TYPE(klass), GNT_BINDABLE_CLASS(klass)); | |
808 GNTDEBUG; | |
809 } | |
810 | |
811 static void | |
812 gnt_entry_init(GTypeInstance *instance, gpointer class) | |
813 { | |
814 GntWidget *widget = GNT_WIDGET(instance); | |
815 GntEntry *entry = GNT_ENTRY(instance); | |
816 | |
817 entry->flag = GNT_ENTRY_FLAG_ALL; | |
818 entry->max = 0; | |
819 | |
820 entry->histlength = 0; | |
821 entry->history = NULL; | |
822 | |
823 entry->word = TRUE; | |
824 entry->always = FALSE; | |
825 entry->suggests = NULL; | |
826 | |
827 GNT_WIDGET_SET_FLAGS(GNT_WIDGET(entry), | |
828 GNT_WIDGET_NO_BORDER | GNT_WIDGET_NO_SHADOW | GNT_WIDGET_CAN_TAKE_FOCUS); | |
829 GNT_WIDGET_SET_FLAGS(GNT_WIDGET(entry), GNT_WIDGET_GROW_X); | |
830 | |
831 widget->priv.minw = 3; | |
832 widget->priv.minh = 1; | |
833 | |
834 GNTDEBUG; | |
835 } | |
836 | |
837 /****************************************************************************** | |
838 * GntEntry API | |
839 *****************************************************************************/ | |
840 GType | |
841 gnt_entry_get_gtype(void) | |
842 { | |
843 static GType type = 0; | |
844 | |
845 if(type == 0) | |
846 { | |
847 static const GTypeInfo info = { | |
848 sizeof(GntEntryClass), | |
849 NULL, /* base_init */ | |
850 NULL, /* base_finalize */ | |
851 (GClassInitFunc)gnt_entry_class_init, | |
852 NULL, /* class_finalize */ | |
853 NULL, /* class_data */ | |
854 sizeof(GntEntry), | |
855 0, /* n_preallocs */ | |
856 gnt_entry_init, /* instance_init */ | |
857 NULL /* value_table */ | |
858 }; | |
859 | |
860 type = g_type_register_static(GNT_TYPE_WIDGET, | |
861 "GntEntry", | |
862 &info, 0); | |
863 } | |
864 | |
865 return type; | |
866 } | |
867 | |
868 GntWidget *gnt_entry_new(const char *text) | |
869 { | |
870 GntWidget *widget = g_object_new(GNT_TYPE_ENTRY, NULL); | |
871 GntEntry *entry = GNT_ENTRY(widget); | |
872 | |
873 gnt_entry_set_text_internal(entry, text); | |
874 | |
875 return widget; | |
876 } | |
877 | |
878 static void | |
879 gnt_entry_set_text_internal(GntEntry *entry, const char *text) | |
880 { | |
881 int len; | |
882 int scroll, cursor; | |
883 | |
884 g_free(entry->start); | |
885 | |
886 if (text && text[0]) | |
887 { | |
888 len = strlen(text); | |
889 } | |
890 else | |
891 { | |
892 len = 0; | |
893 } | |
894 | |
895 entry->buffer = len + 128; | |
896 | |
897 scroll = entry->scroll - entry->start; | |
898 cursor = entry->end - entry->cursor; | |
899 | |
900 entry->start = g_new0(char, entry->buffer); | |
901 if (text) | |
902 snprintf(entry->start, len + 1, "%s", text); | |
903 entry->end = entry->start + len; | |
904 | |
905 entry->scroll = entry->start + scroll; | |
906 entry->cursor = entry->end - cursor; | |
907 | |
908 if (GNT_WIDGET_IS_FLAG_SET(GNT_WIDGET(entry), GNT_WIDGET_MAPPED)) | |
909 entry_redraw(GNT_WIDGET(entry)); | |
910 } | |
911 | |
912 void gnt_entry_set_text(GntEntry *entry, const char *text) | |
913 { | |
914 gboolean changed = TRUE; | |
915 if (text == NULL && entry->start == NULL) | |
916 changed = FALSE; | |
917 if (text && entry->start && g_utf8_collate(text, entry->start) == 0) | |
918 changed = FALSE; | |
919 gnt_entry_set_text_internal(entry, text); | |
920 if (changed) | |
921 entry_text_changed(entry); | |
922 } | |
923 | |
924 void gnt_entry_set_max(GntEntry *entry, int max) | |
925 { | |
926 entry->max = max; | |
927 } | |
928 | |
929 void gnt_entry_set_flag(GntEntry *entry, GntEntryFlag flag) | |
930 { | |
931 entry->flag = flag; | |
932 /* XXX: Check the existing string to make sure the flags are respected? */ | |
933 } | |
934 | |
935 const char *gnt_entry_get_text(GntEntry *entry) | |
936 { | |
937 return entry->start; | |
938 } | |
939 | |
940 void gnt_entry_clear(GntEntry *entry) | |
941 { | |
942 gnt_entry_set_text_internal(entry, NULL); | |
943 entry->scroll = entry->cursor = entry->end = entry->start; | |
944 entry_redraw(GNT_WIDGET(entry)); | |
945 destroy_suggest(entry); | |
946 entry_text_changed(entry); | |
947 } | |
948 | |
949 void gnt_entry_set_masked(GntEntry *entry, gboolean set) | |
950 { | |
951 entry->masked = set; | |
952 } | |
953 | |
954 void gnt_entry_add_to_history(GntEntry *entry, const char *text) | |
955 { | |
956 g_return_if_fail(entry->history != NULL); /* Need to set_history_length first */ | |
957 | |
958 if (g_list_length(entry->history) >= entry->histlength) | |
959 return; | |
960 | |
961 entry->history = g_list_first(entry->history); | |
962 g_free(entry->history->data); | |
963 entry->history->data = g_strdup(text); | |
964 entry->history = g_list_prepend(entry->history, NULL); | |
965 } | |
966 | |
967 void gnt_entry_set_history_length(GntEntry *entry, int num) | |
968 { | |
969 if (num == 0) | |
970 { | |
971 entry->histlength = num; | |
972 if (entry->history) | |
973 { | |
974 entry->history = g_list_first(entry->history); | |
975 g_list_foreach(entry->history, (GFunc)g_free, NULL); | |
976 g_list_free(entry->history); | |
977 entry->history = NULL; | |
978 } | |
979 return; | |
980 } | |
981 | |
982 if (entry->histlength == 0) | |
983 { | |
984 entry->histlength = num; | |
985 entry->history = g_list_append(NULL, NULL); | |
986 return; | |
987 } | |
988 | |
989 if (num > 0 && num < entry->histlength) | |
990 { | |
991 GList *first, *iter; | |
992 int index = 0; | |
993 for (first = entry->history, index = 0; first->prev; first = first->prev, index++); | |
994 while ((iter = g_list_nth(first, num)) != NULL) | |
995 { | |
996 g_free(iter->data); | |
997 first = g_list_delete_link(first, iter); | |
998 } | |
999 entry->histlength = num; | |
1000 if (index >= num) | |
1001 entry->history = g_list_last(first); | |
1002 return; | |
1003 } | |
1004 | |
1005 entry->histlength = num; | |
1006 } | |
1007 | |
1008 void gnt_entry_set_word_suggest(GntEntry *entry, gboolean word) | |
1009 { | |
1010 entry->word = word; | |
1011 } | |
1012 | |
1013 void gnt_entry_set_always_suggest(GntEntry *entry, gboolean always) | |
1014 { | |
1015 entry->always = always; | |
1016 } | |
1017 | |
1018 void gnt_entry_add_suggest(GntEntry *entry, const char *text) | |
1019 { | |
1020 GList *find; | |
1021 | |
1022 if (!text || !*text) | |
1023 return; | |
1024 | |
1025 find = g_list_find_custom(entry->suggests, text, (GCompareFunc)g_utf8_collate); | |
1026 if (find) | |
1027 return; | |
1028 entry->suggests = g_list_append(entry->suggests, g_strdup(text)); | |
1029 } | |
1030 | |
1031 void gnt_entry_remove_suggest(GntEntry *entry, const char *text) | |
1032 { | |
1033 GList *find = g_list_find_custom(entry->suggests, text, (GCompareFunc)g_utf8_collate); | |
1034 if (find) | |
1035 { | |
1036 g_free(find->data); | |
1037 entry->suggests = g_list_delete_link(entry->suggests, find); | |
1038 } | |
1039 } | |
1040 |