[pan2: 24/68] Fix Bug351196 add regex support to search
- From: Petr Kovář <pmkovar src gnome org>
- To: commits-list gnome org
- Cc:
- Subject: [pan2: 24/68] Fix Bug351196 add regex support to search
- Date: Tue, 8 Feb 2011 23:00:02 +0000 (UTC)
commit ae201588afffcc966c2410d03da6e82b8ebf5aa9
Author: K. Haley <haleykd users sf net>
Date: Wed Mar 24 18:17:09 2010 -0600
Fix Bug351196 add regex support to search
This adds regex support to the group and header search boxes. There
is a menu accessed through the icon on the left of the entry that
toggles regex support. There is also a pref "use-regex" that sets
the default mode.
Jack Cuyler wrote the original patch.
pan/gui/group-pane.cc | 87 +++++++++++++++++++++++++++++++++++++++++-------
pan/gui/group-pane.h | 2 +-
pan/gui/header-pane.cc | 18 +++++++++-
3 files changed, 93 insertions(+), 14 deletions(-)
---
diff --git a/pan/gui/group-pane.cc b/pan/gui/group-pane.cc
index c10aba3..81e3247 100644
--- a/pan/gui/group-pane.cc
+++ b/pan/gui/group-pane.cc
@@ -493,10 +493,21 @@ namespace
gtk_tree_path_free (path);
}
}
+ const char * mode_strings [] =
+ {
+ N_("Group"),
+ N_("Group (regex)")
+ };
+
+ enum
+ {
+ GROUP,
+ GROUP_REGEX
+ };
}
void
-GroupPane :: set_filter (const std::string& search_text)
+GroupPane :: set_filter (const std::string& search_text, int mode)
{
GtkTreeView * view = GTK_TREE_VIEW(_tree_view);
@@ -508,7 +519,10 @@ GroupPane :: set_filter (const std::string& search_text)
TextMatch match;
TextMatch * pmatch (0);
if (!search_text.empty()) {
- match.set (search_text, TextMatch::CONTAINS, false);
+ if (mode == GROUP)
+ match.set (search_text, TextMatch::CONTAINS, false);
+ else if (mode == GROUP_REGEX)
+ match.set (search_text, TextMatch::REGEX, false);
pmatch = &match;
}
@@ -539,6 +553,7 @@ namespace
guint activate_soon_tag (0u);
std::string search_text;
+ int mode;
void set_search_entry (GtkWidget * entry, const char * s)
{
@@ -564,7 +579,7 @@ namespace
c.pixel = 0;
c.red = c.green = c.blue = 0xAAAA; // light grey
gtk_widget_modify_text (w, GTK_STATE_NORMAL, &c);
- set_search_entry (w, _("Group Name"));
+ set_search_entry (w, _(mode_strings[mode]));
}
}
@@ -578,7 +593,7 @@ namespace
void search_activate (GroupPane * pane)
{
- pane->set_filter (search_text);
+ pane->set_filter (search_text, mode);
}
void remove_activate_soon_tag ()
@@ -596,12 +611,21 @@ namespace
remove_activate_soon_tag ();
}
- void clear_button_clicked_cb (GtkEntry * e, GtkEntryIconPosition, GdkEventButton *, gpointer pane_gpointer)
+ void entry_icon_released (GtkEntry*, GtkEntryIconPosition icon_pos, GdkEventButton *, gpointer menu)
{
- set_search_entry (GTK_WIDGET(e), "");
- refresh_search_entry (GTK_WIDGET(e));
- search_text.clear ();
- search_entry_activated (NULL, pane_gpointer);
+ if (icon_pos == GTK_ENTRY_ICON_PRIMARY)
+ gtk_menu_popup (GTK_MENU(menu), 0, 0, 0, 0, 0, gtk_get_current_event_time());
+ }
+
+ void clear_button_clicked_cb (GtkEntry * e, GtkEntryIconPosition icon_pos, GdkEventButton *, gpointer pane_gpointer)
+ {
+ if (icon_pos == GTK_ENTRY_ICON_SECONDARY)
+ {
+ set_search_entry (GTK_WIDGET(e), "");
+ refresh_search_entry (GTK_WIDGET(e));
+ search_text.clear ();
+ search_entry_activated (NULL, pane_gpointer);
+ }
}
gboolean activated_timeout_cb (gpointer pane_gpointer)
@@ -622,6 +646,21 @@ namespace
search_text = gtk_entry_get_text (GTK_ENTRY(e));
bump_activate_soon_tag (static_cast<GroupPane*>(pane_gpointer));
}
+
+ // when the search mode is changed via the menu,
+ // update our state variable and bump the activate timeout.
+ void search_menu_toggled_cb (GtkCheckMenuItem * menu_item,
+ gpointer entry_g)
+ {
+ if (gtk_check_menu_item_get_active (menu_item))
+ {
+ mode = GPOINTER_TO_INT (g_object_get_data (G_OBJECT(menu_item), "MODE"));
+ refresh_search_entry (GTK_WIDGET(entry_g));
+ GroupPane * h = (GroupPane*) g_object_get_data (
+ G_OBJECT(entry_g), "group-pane");
+ bump_activate_soon_tag (h);
+ }
+ }
}
void
@@ -656,7 +695,7 @@ namespace
g_snprintf (buf, sizeof(buf), " (%lu)", unread);
group_name += buf;
}
- //if (unread || total) {
+ //if (unread || total)
//if (unread)
// g_snprintf (buf, sizeof(buf), _(" (%lu of %lu)"), unread, total);
//else
@@ -799,14 +838,38 @@ GroupPane :: create_filter_entry ()
gtk_entry_set_icon_from_stock( GTK_ENTRY( entry ),
GTK_ENTRY_ICON_SECONDARY,
GTK_STOCK_CLEAR );
- gtk_widget_set_size_request (entry, 133, -1);
-
+ gtk_entry_set_icon_from_stock( GTK_ENTRY( entry ),
+ GTK_ENTRY_ICON_PRIMARY,
+ GTK_STOCK_FIND );
+// gtk_widget_set_size_request (entry, 133, -1);
_action_manager.disable_accelerators_when_focused (entry);
g_signal_connect (entry, "focus-in-event", G_CALLBACK(search_entry_focus_in_cb), NULL);
g_signal_connect (entry, "focus-out-event", G_CALLBACK(search_entry_focus_out_cb), NULL);
g_signal_connect (entry, "activate", G_CALLBACK(search_entry_activated), this);
g_signal_connect (entry, "icon-release", G_CALLBACK(clear_button_clicked_cb), this);
entry_changed_tag = g_signal_connect (entry, "changed", G_CALLBACK(search_entry_changed_by_user), this);
+
+ GtkWidget * menu = gtk_menu_new ();
+ bool regex = _prefs.get_flag ("use-regex", false);
+ if ( regex == true )
+ mode = 1;
+ else
+ mode = 0;
+ GSList * l = 0;
+ for (int i=0, qty=G_N_ELEMENTS(mode_strings); i<qty; ++i)
+ {
+ GtkWidget * w = gtk_radio_menu_item_new_with_label (l, _(mode_strings[i]));
+ l = gtk_radio_menu_item_get_group (GTK_RADIO_MENU_ITEM(w));
+ g_object_set_data (G_OBJECT(w), "MODE", GINT_TO_POINTER(i));
+ g_signal_connect (w, "toggled", G_CALLBACK(search_menu_toggled_cb),entry);
+ if (mode == i)
+ gtk_check_menu_item_set_active (GTK_CHECK_MENU_ITEM(w), TRUE);
+ gtk_menu_shell_append (GTK_MENU_SHELL(menu), w);
+ gtk_widget_show (w);
+ }
+ g_signal_connect (entry, "icon-release", G_CALLBACK(entry_icon_released), menu);
+ g_object_set_data (G_OBJECT(entry), "group-pane", this);
+
refresh_search_entry (entry);
return entry;
}
diff --git a/pan/gui/group-pane.h b/pan/gui/group-pane.h
index 78c1663..0e77866 100644
--- a/pan/gui/group-pane.h
+++ b/pan/gui/group-pane.h
@@ -77,7 +77,7 @@ namespace pan
void refresh_font ();
public: // pretend these are private
- void set_filter (const std::string& text);
+ void set_filter (const std::string& text, int mode);
const ActionManager& _action_manager;
private:
diff --git a/pan/gui/header-pane.cc b/pan/gui/header-pane.cc
index 961a8b4..e0ee674 100644
--- a/pan/gui/header-pane.cc
+++ b/pan/gui/header-pane.cc
@@ -1008,6 +1008,7 @@ namespace
const char * mode_strings [] =
{
N_("Subject or Author"),
+ N_("Sub or Auth (regex)"),
N_("Subject"),
N_("Author"),
N_("Message-ID"),
@@ -1016,6 +1017,7 @@ namespace
enum
{
SUBJECT_OR_AUTHOR,
+ SUBJECT_OR_AUTHOR_REGEX,
SUBJECT,
AUTHOR,
MESSAGE_ID
@@ -1051,6 +1053,14 @@ HeaderPane :: rebuild_filter (const std::string& text, int mode)
f2.set_type_text ("From", d);
entry_filter._aggregates.push_back (f1);
entry_filter._aggregates.push_back (f2);
+ } else if (mode == SUBJECT_OR_AUTHOR_REGEX) {
+ FilterInfo f1, f2;
+ entry_filter.set_type_aggregate_or ();
+ d.type = TextMatch::REGEX;
+ f1.set_type_text ("Subject", d);
+ f2.set_type_text ("From", d);
+ entry_filter._aggregates.push_back (f1);
+ entry_filter._aggregates.push_back (f2);
}
f._aggregates.push_back (entry_filter);
}
@@ -1499,14 +1509,20 @@ HeaderPane :: create_filter_entry ()
GTK_ENTRY_ICON_SECONDARY,
GTK_STOCK_CLEAR );
+ bool regex = _prefs.get_flag ("use-regex", false);
GtkWidget * menu = gtk_menu_new ();
- mode = 0;
+ if (regex == true )
+ mode = 1;
+ else
+ mode = 0;
GSList * l = 0;
for (int i=0, qty=G_N_ELEMENTS(mode_strings); i<qty; ++i) {
GtkWidget * w = gtk_radio_menu_item_new_with_label (l, _(mode_strings[i]));
l = gtk_radio_menu_item_get_group (GTK_RADIO_MENU_ITEM(w));
g_object_set_data (G_OBJECT(w), "MODE", GINT_TO_POINTER(i));
g_signal_connect (w, "toggled", G_CALLBACK(search_menu_toggled_cb),entry);
+ if (mode == i)
+ gtk_check_menu_item_set_active (GTK_CHECK_MENU_ITEM(w), TRUE);
gtk_menu_shell_append (GTK_MENU_SHELL(menu), w);
gtk_widget_show (w);
}
[
Date Prev][
Date Next] [
Thread Prev][
Thread Next]
[
Thread Index]
[
Date Index]
[
Author Index]