[anjuta] Regex search patch.



commit 074edb66b708748bc78a40518fc484216924e5e1
Author: Eugenia <genia likes science gmail com>
Date:   Wed Mar 2 14:05:41 2011 -0600

    Regex search patch.

 plugins/document-manager/action-callbacks.c        |   19 ++
 plugins/document-manager/action-callbacks.h        |    2 +
 .../document-manager/anjuta-document-manager.xml   |    2 +
 plugins/document-manager/plugin.c                  |   14 ++-
 plugins/document-manager/search-box.c              |  216 +++++++++++++++++++-
 plugins/document-manager/search-box.h              |    1 +
 6 files changed, 247 insertions(+), 7 deletions(-)
---
diff --git a/plugins/document-manager/action-callbacks.c b/plugins/document-manager/action-callbacks.c
index 7b3114e..da9f714 100644
--- a/plugins/document-manager/action-callbacks.c
+++ b/plugins/document-manager/action-callbacks.c
@@ -978,6 +978,25 @@ on_search_popup_clear_highlight (GtkAction *action, gpointer user_data)
 }
 
 void
+on_search_popup_regex_search (GtkAction *action, gpointer user_data)
+{
+	DocmanPlugin *plugin;
+	GtkWidget *search_box;
+
+	gboolean regex_active = gtk_toggle_action_get_active (GTK_TOGGLE_ACTION (action));
+	plugin = ANJUTA_PLUGIN_DOCMAN (user_data);
+
+	search_box = plugin->search_box;
+	if (!gtk_widget_get_parent (search_box))
+		gtk_box_pack_end (GTK_BOX (plugin->vbox), search_box, FALSE, FALSE, 0);
+
+	if (!gtk_widget_get_visible (search_box))
+		gtk_widget_show (search_box);
+
+	search_box_toggle_regex (SEARCH_BOX (search_box), regex_active);
+}
+
+void
 on_editor_add_view_activate (GtkAction *action, gpointer user_data)
 {
 	IAnjutaDocument *doc;
diff --git a/plugins/document-manager/action-callbacks.h b/plugins/document-manager/action-callbacks.h
index 91ceef0..fba2e87 100644
--- a/plugins/document-manager/action-callbacks.h
+++ b/plugins/document-manager/action-callbacks.h
@@ -101,6 +101,8 @@ void on_search_popup_case_sensitive_toggle (GtkAction *action, gpointer user_dat
 void on_search_popup_highlight_toggle (GtkAction *action, gpointer user_data);
 void on_search_popup_clear_highlight (GtkAction *action, gpointer user_data);
 
+void on_search_popup_regex_search (GtkAction *action, gpointer user_data);
+
 void on_next_document (GtkAction *action, gpointer user_data);
 void on_previous_document (GtkAction *action, gpointer user_data);
 
diff --git a/plugins/document-manager/anjuta-document-manager.xml b/plugins/document-manager/anjuta-document-manager.xml
index a64359e..fd40cf9 100644
--- a/plugins/document-manager/anjuta-document-manager.xml
+++ b/plugins/document-manager/anjuta-document-manager.xml
@@ -182,5 +182,7 @@
 		<separator name="separator29"/>
 		<menuitem name="HighlightAll" action="ActionSearchboxPopupHighlightAll" />
 		<menuitem name="ClearHighlight" action="ActionSearchboxPopupClearHighlight" />
+		<separator name="separator30"/>
+		<menuitem name="Regex Search" action="ActionSearchboxRegexSearch" />
 	</popup>
 </ui>
diff --git a/plugins/document-manager/plugin.c b/plugins/document-manager/plugin.c
index 369327c..36f012e 100644
--- a/plugins/document-manager/plugin.c
+++ b/plugins/document-manager/plugin.c
@@ -289,7 +289,11 @@ static GtkToggleActionEntry actions_searchbox_popup[] = {
   { "ActionSearchboxPopupHighlightAll", GTK_STOCK_FIND, 
     N_("Highlight All"), NULL, 
     N_("Highlight all occurrences"),
-	G_CALLBACK (on_search_popup_highlight_toggle)}
+	G_CALLBACK (on_search_popup_highlight_toggle)},
+  { "ActionSearchboxRegexSearch", GTK_STOCK_FIND,
+	N_("RegEx Search"), NULL,
+	N_("Regular expression search"),
+	G_CALLBACK (on_search_popup_regex_search)}
 };
 
 
@@ -888,6 +892,14 @@ update_document_ui_interface_items (AnjutaPlugin *plugin, IAnjutaDocument *doc)
 	action = anjuta_ui_get_action (ui,  "ActionGroupEditorSearchOptions",
 								   "ActionSearchboxPopupHighlightAll");
 	g_object_set (G_OBJECT (action), "sensitive", flag, NULL);
+	action = anjuta_ui_get_action (ui,  "ActionGroupEditorSearchOptions",
+								   "ActionSearchboxRegexSearch");
+	g_object_set (G_OBJECT (action), "sensitive", flag, NULL);
+	/*
+	action = anjuta_ui_get_action (ui,  "ActionGroupEditorSearchType",
+								   "ActionSearchboxNormalSearch");
+	g_object_set (G_OBJECT (action), "sensitive", flag, NULL);
+*/
 
 	/* IAnjutaEditorAssist */
 	flag = IANJUTA_IS_EDITOR_ASSIST (doc);
diff --git a/plugins/document-manager/search-box.c b/plugins/document-manager/search-box.c
index 0568527..d6b2049 100644
--- a/plugins/document-manager/search-box.c
+++ b/plugins/document-manager/search-box.c
@@ -65,6 +65,7 @@ struct _SearchBoxPrivate
 	GtkWidget* popup_menu;
 	gboolean case_sensitive;
 	gboolean highlight_all;	
+	gboolean regex_mode;
 
 	/* Incremental search */
 	IAnjutaIterable* last_start;
@@ -241,6 +242,39 @@ on_search_focus_out (GtkWidget* widget, GdkEvent* event, SearchBox* search_box)
 }
 
 
+
+static gboolean
+incremental_regex_search (const gchar* search_entry, const gchar* editor_text, gint * start_pos, gint * end_pos)
+{
+	GRegex * regex;
+	GMatchInfo *match_info;
+	gboolean result;
+	GError * err = NULL;
+
+	regex = g_regex_new (search_entry, 0, 0, &err);
+	if (err)
+	{
+		g_message ("%s",err->message);
+		g_error_free (err);
+		g_regex_unref(regex);
+		return FALSE;
+	}
+
+	g_regex_match (regex, editor_text, 0, &match_info);
+	result = g_match_info_fetch_pos(match_info, 0, start_pos, end_pos);
+
+	*start_pos = g_utf8_pointer_to_offset(editor_text, &editor_text[*start_pos]);
+	*end_pos = g_utf8_pointer_to_offset(editor_text, &editor_text[*end_pos]);
+
+	if (regex)
+		g_regex_unref(regex);
+	if (match_info)
+		g_match_info_free (match_info);
+
+	return result;
+
+}
+
 gboolean
 search_box_incremental_search (SearchBox* search_box, gboolean search_forward)
 {
@@ -293,7 +327,27 @@ search_box_incremental_search (SearchBox* search_box, gboolean search_forward)
 		{
 			gchar* selected_text =
 				ianjuta_editor_selection_get (selection, NULL);
-			if (private->case_sensitive)
+
+			if (private->regex_mode)
+			{
+				gint start_pos, end_pos;
+				gboolean result = incremental_regex_search (search_text, selected_text, &start_pos, &end_pos);
+
+				if (result)
+				{
+					if (search_forward)
+					{
+						ianjuta_iterable_next (IANJUTA_ITERABLE (search_start), NULL);
+					}
+					else
+					{
+						search_end = IANJUTA_EDITOR_CELL (ianjuta_editor_selection_get_end (selection, NULL));
+						ianjuta_iterable_previous (IANJUTA_ITERABLE (search_end), NULL);
+						ianjuta_iterable_first (IANJUTA_ITERABLE (search_start), NULL);
+					}
+				}
+			}
+			else if (private->case_sensitive)
 			{
 				if (g_str_has_prefix (selected_text, search_text))
 				{
@@ -333,7 +387,126 @@ search_box_incremental_search (SearchBox* search_box, gboolean search_forward)
 		}
 	}
 
-	if (search_forward)
+	if (private->regex_mode)
+	{
+		gint start_pos, end_pos;
+		gchar * text_to_search, * text_to_reverse;
+		gboolean result;
+
+		if (search_forward)
+		{
+			text_to_search = ianjuta_editor_get_text (private->current_editor,
+													IANJUTA_ITERABLE(search_start),
+													IANJUTA_ITERABLE(search_end), NULL);
+			result = incremental_regex_search (search_text, text_to_search, &start_pos, &end_pos);
+
+			start_pos += ianjuta_iterable_get_position(IANJUTA_ITERABLE(search_start), NULL);
+			end_pos += ianjuta_iterable_get_position(IANJUTA_ITERABLE(search_start), NULL);
+
+		}
+		else
+		{
+			text_to_reverse = ianjuta_editor_get_text (private->current_editor,
+													IANJUTA_ITERABLE(search_end),
+													IANJUTA_ITERABLE(search_start), NULL);
+
+			if (g_utf8_validate (text_to_reverse, strlen(text_to_reverse), NULL))
+			{
+				text_to_search = g_utf8_strreverse(text_to_reverse, strlen( text_to_reverse ));
+
+				result = incremental_regex_search (search_text, text_to_search, &start_pos, &end_pos);
+
+				start_pos = ianjuta_iterable_get_position(IANJUTA_ITERABLE(search_end), NULL) - start_pos;
+				end_pos = ianjuta_iterable_get_position(IANJUTA_ITERABLE(search_end), NULL) - end_pos;
+			}
+
+		}
+
+		if (result && start_pos >= 0)
+		{
+
+			result_start = IANJUTA_EDITOR_CELL (ianjuta_editor_get_start_position (private->current_editor,
+																	   NULL));
+			result_end = IANJUTA_EDITOR_CELL (ianjuta_editor_get_start_position (private->current_editor,
+																	   NULL));
+
+			if (ianjuta_iterable_set_position(IANJUTA_ITERABLE(result_start), start_pos, NULL) &&
+				ianjuta_iterable_set_position(IANJUTA_ITERABLE(result_end), end_pos, NULL))
+			{
+				found = TRUE;
+				anjuta_status_pop (ANJUTA_STATUS (private->status));
+			}
+			else
+			{
+				result_start = NULL;
+				result_end = NULL;
+			}
+		}
+		else
+		{
+			/* Try to wrap search around */
+			if (search_forward)
+			{
+				ianjuta_iterable_first (IANJUTA_ITERABLE (search_start), NULL);
+
+				text_to_search = ianjuta_editor_get_text (private->current_editor,
+													IANJUTA_ITERABLE(search_start),
+													IANJUTA_ITERABLE(search_end), NULL);
+
+				result = incremental_regex_search (search_text, text_to_search, &start_pos, &end_pos);
+
+				start_pos += ianjuta_iterable_get_position(IANJUTA_ITERABLE(search_start), NULL);
+				end_pos += ianjuta_iterable_get_position(IANJUTA_ITERABLE(search_start), NULL);
+			}
+			else
+			{
+				search_end = IANJUTA_EDITOR_CELL (ianjuta_editor_get_end_position (private->current_editor,
+																	   NULL));
+				search_start = IANJUTA_EDITOR_CELL (ianjuta_editor_get_start_position (private->current_editor,
+																	   NULL));
+
+				text_to_reverse = ianjuta_editor_get_text (private->current_editor,
+													IANJUTA_ITERABLE(search_end),
+													IANJUTA_ITERABLE(search_start), NULL);
+
+				if (g_utf8_validate (text_to_reverse, strlen(text_to_reverse), NULL))
+				{
+					text_to_search = g_utf8_strreverse(text_to_reverse, strlen( text_to_reverse ));
+
+					result = incremental_regex_search (search_text, text_to_search, &start_pos, &end_pos);
+
+					start_pos = ianjuta_iterable_get_position(IANJUTA_ITERABLE(search_end), NULL) - start_pos;
+					end_pos = ianjuta_iterable_get_position(IANJUTA_ITERABLE(search_end), NULL) - end_pos;
+				}
+			}
+
+			result_start = IANJUTA_EDITOR_CELL (ianjuta_editor_get_start_position (private->current_editor,
+																	   NULL));
+			result_end = IANJUTA_EDITOR_CELL (ianjuta_editor_get_start_position (private->current_editor,
+																	   NULL));
+
+			if (ianjuta_iterable_set_position(IANJUTA_ITERABLE(result_start), start_pos, NULL) &&
+				ianjuta_iterable_set_position(IANJUTA_ITERABLE(result_end), end_pos, NULL))
+			{
+				if (ianjuta_iterable_compare (IANJUTA_ITERABLE (result_start),
+				                              real_start, NULL) != 0)
+				{
+					found = TRUE;
+					anjuta_status_push (private->status,
+					                    _("Search for \"%s\" reached the end and wrapped around."), search_text);
+				}
+				else if (ianjuta_editor_selection_has_selection (selection, NULL))
+				{
+					anjuta_status_pop (private->status);
+					anjuta_status_push (private->status,
+					                    _("Search for \"%s\" reached the end and wrapped around but no new match was found."), search_text);
+				}
+			}
+
+		}
+
+	}
+	else if (search_forward)
 	{
 		if (ianjuta_editor_search_forward (IANJUTA_EDITOR_SEARCH (private->current_editor),
 		                                   search_text, private->case_sensitive,
@@ -348,6 +521,7 @@ search_box_incremental_search (SearchBox* search_box, gboolean search_forward)
 		{
 			/* Try to continue on top */
 			ianjuta_iterable_first (IANJUTA_ITERABLE (search_start), NULL);
+
 			if (ianjuta_editor_search_forward (IANJUTA_EDITOR_SEARCH (private->current_editor),
 			                                   search_text, private->case_sensitive,
 			                                   search_start, search_end, 
@@ -385,8 +559,10 @@ search_box_incremental_search (SearchBox* search_box, gboolean search_forward)
 		else
 		{
 			/* Try to continue on buttom */
-			ianjuta_iterable_last (IANJUTA_ITERABLE (search_end), NULL);
-			ianjuta_iterable_first (IANJUTA_ITERABLE (search_start), NULL);			
+			search_end = IANJUTA_EDITOR_CELL (ianjuta_editor_get_end_position (private->current_editor,
+																	   NULL));
+			search_start = IANJUTA_EDITOR_CELL (ianjuta_editor_get_start_position (private->current_editor,
+																	   NULL));
 			if (ianjuta_editor_search_backward (IANJUTA_EDITOR_SEARCH (private->current_editor),
 			                                   search_text, private->case_sensitive,
 			                                   search_end, search_start, 
@@ -422,7 +598,7 @@ search_box_incremental_search (SearchBox* search_box, gboolean search_forward)
 	search_box_set_entry_color (search_box, found);	
 	g_object_unref (real_start);
 	g_object_unref (search_end);
-		
+
 	if (private->last_start)
 	{
 		g_object_unref (private->last_start);
@@ -456,6 +632,11 @@ search_box_toggle_highlight (SearchBox * search_box, gboolean status)
 		return;
 
 	private->highlight_all = status;
+
+	if (!status)
+	{
+		ianjuta_indicable_clear(IANJUTA_INDICABLE(private->current_editor), NULL);
+	}
 }
 
 void 
@@ -469,6 +650,18 @@ search_box_toggle_case_sensitive (SearchBox * search_box, gboolean status)
 	private->case_sensitive = status;
 }
 
+void
+search_box_toggle_regex (SearchBox * search_box, gboolean status)
+{
+	SearchBoxPrivate* private = GET_PRIVATE(search_box);
+
+	if (!private->current_editor)
+		return;
+
+	private->regex_mode = status;
+
+}
+
 static void
 search_box_search_highlight_all (SearchBox * search_box, gboolean search_forward)
 {
@@ -513,7 +706,12 @@ search_box_search_highlight_all (SearchBox * search_box, gboolean search_forward
 static void
 on_search_box_document_changed (GtkWidget * widget, SearchBox * search_box)
 {
-	search_box_incremental_search (search_box, TRUE);
+	SearchBoxPrivate* private = GET_PRIVATE(search_box);
+
+	if (!private->regex_mode)
+	{
+		search_box_incremental_search (search_box, TRUE);
+	}
 }
 
 static void
@@ -529,6 +727,7 @@ on_search_box_forward_search (GtkWidget * widget, SearchBox * search_box)
 	{
 		search_box_incremental_search (search_box, TRUE);
 	}
+
 }
 
 static void
@@ -732,6 +931,11 @@ search_box_init (SearchBox *object)
 	g_signal_connect (G_OBJECT(private->replace_all_button), "clicked", 
 					G_CALLBACK (on_replace_all_activated), object);
 
+	/* Popup Menu Options */
+	private->regex_mode = FALSE;
+	private->highlight_all = FALSE;
+	private->case_sensitive = FALSE;
+
 	/* Initialize search_box grid */
 	private->grid = gtk_grid_new();
 	gtk_orientable_set_orientation (GTK_ORIENTABLE (private->grid), 
diff --git a/plugins/document-manager/search-box.h b/plugins/document-manager/search-box.h
index 8032e0e..874bb76 100644
--- a/plugins/document-manager/search-box.h
+++ b/plugins/document-manager/search-box.h
@@ -63,6 +63,7 @@ gboolean search_box_incremental_search (SearchBox* search_box, gboolean search_f
 void search_box_clear_highlight (SearchBox * search_box);
 void search_box_toggle_highlight (SearchBox * search_box, gboolean status);
 void search_box_toggle_case_sensitive (SearchBox * search_box, gboolean status);
+void search_box_toggle_regex (SearchBox * search_box, gboolean status);
 
 G_END_DECLS
 



[Date Prev][Date Next]   [Thread Prev][Thread Next]   [Thread Index] [Date Index] [Author Index]