add new marshallers used by the text widget
2000-10-26 Havoc Pennington <hp@redhat.com> * gtk/gtkmarshal.list: add new marshallers used by the text widget * gtk/gtktextbuffer.c (gtk_text_buffer_class_init): fix marshaller types * gtk/gtktexttagtable.c (gtk_text_tag_table_class_init): fix marshaller types * gtk/gtktextlayout.h, gtk/gtktextlayout.c, gtk/gtktextdisplay.h, gtk/gtktextdisplay.c: We need to preserve Tk copyrights and license on these files. * gtk/gtktextiter.c (gtk_text_iter_backward_search): Make this work. * gtk/gtktextbtree.c (gtk_text_btree_new): init stamps to runtime random number different for each tree, instead of a constant I made up.
This commit is contained in:

committed by
Havoc Pennington

parent
e279178d1a
commit
a291b0be4c
21
ChangeLog
21
ChangeLog
@ -1,3 +1,24 @@
|
||||
2000-10-26 Havoc Pennington <hp@redhat.com>
|
||||
|
||||
* gtk/gtkmarshal.list: add new marshallers used by the text widget
|
||||
|
||||
* gtk/gtktextbuffer.c (gtk_text_buffer_class_init): fix marshaller
|
||||
types
|
||||
|
||||
* gtk/gtktexttagtable.c (gtk_text_tag_table_class_init): fix
|
||||
marshaller types
|
||||
|
||||
* gtk/gtktextlayout.h, gtk/gtktextlayout.c, gtk/gtktextdisplay.h,
|
||||
gtk/gtktextdisplay.c: We need to preserve Tk copyrights and
|
||||
license on these files.
|
||||
|
||||
* gtk/gtktextiter.c (gtk_text_iter_backward_search): Make this
|
||||
work.
|
||||
|
||||
* gtk/gtktextbtree.c (gtk_text_btree_new): init stamps to
|
||||
runtime random number different for each tree, instead of
|
||||
a constant I made up.
|
||||
|
||||
Thu Oct 26 07:36:16 2000 Tim Janik <timj@gtk.org>
|
||||
|
||||
* gtk/Makefile.am: buncha cleanups, kludged build sources
|
||||
|
@ -1,3 +1,24 @@
|
||||
2000-10-26 Havoc Pennington <hp@redhat.com>
|
||||
|
||||
* gtk/gtkmarshal.list: add new marshallers used by the text widget
|
||||
|
||||
* gtk/gtktextbuffer.c (gtk_text_buffer_class_init): fix marshaller
|
||||
types
|
||||
|
||||
* gtk/gtktexttagtable.c (gtk_text_tag_table_class_init): fix
|
||||
marshaller types
|
||||
|
||||
* gtk/gtktextlayout.h, gtk/gtktextlayout.c, gtk/gtktextdisplay.h,
|
||||
gtk/gtktextdisplay.c: We need to preserve Tk copyrights and
|
||||
license on these files.
|
||||
|
||||
* gtk/gtktextiter.c (gtk_text_iter_backward_search): Make this
|
||||
work.
|
||||
|
||||
* gtk/gtktextbtree.c (gtk_text_btree_new): init stamps to
|
||||
runtime random number different for each tree, instead of
|
||||
a constant I made up.
|
||||
|
||||
Thu Oct 26 07:36:16 2000 Tim Janik <timj@gtk.org>
|
||||
|
||||
* gtk/Makefile.am: buncha cleanups, kludged build sources
|
||||
|
@ -1,3 +1,24 @@
|
||||
2000-10-26 Havoc Pennington <hp@redhat.com>
|
||||
|
||||
* gtk/gtkmarshal.list: add new marshallers used by the text widget
|
||||
|
||||
* gtk/gtktextbuffer.c (gtk_text_buffer_class_init): fix marshaller
|
||||
types
|
||||
|
||||
* gtk/gtktexttagtable.c (gtk_text_tag_table_class_init): fix
|
||||
marshaller types
|
||||
|
||||
* gtk/gtktextlayout.h, gtk/gtktextlayout.c, gtk/gtktextdisplay.h,
|
||||
gtk/gtktextdisplay.c: We need to preserve Tk copyrights and
|
||||
license on these files.
|
||||
|
||||
* gtk/gtktextiter.c (gtk_text_iter_backward_search): Make this
|
||||
work.
|
||||
|
||||
* gtk/gtktextbtree.c (gtk_text_btree_new): init stamps to
|
||||
runtime random number different for each tree, instead of
|
||||
a constant I made up.
|
||||
|
||||
Thu Oct 26 07:36:16 2000 Tim Janik <timj@gtk.org>
|
||||
|
||||
* gtk/Makefile.am: buncha cleanups, kludged build sources
|
||||
|
@ -1,3 +1,24 @@
|
||||
2000-10-26 Havoc Pennington <hp@redhat.com>
|
||||
|
||||
* gtk/gtkmarshal.list: add new marshallers used by the text widget
|
||||
|
||||
* gtk/gtktextbuffer.c (gtk_text_buffer_class_init): fix marshaller
|
||||
types
|
||||
|
||||
* gtk/gtktexttagtable.c (gtk_text_tag_table_class_init): fix
|
||||
marshaller types
|
||||
|
||||
* gtk/gtktextlayout.h, gtk/gtktextlayout.c, gtk/gtktextdisplay.h,
|
||||
gtk/gtktextdisplay.c: We need to preserve Tk copyrights and
|
||||
license on these files.
|
||||
|
||||
* gtk/gtktextiter.c (gtk_text_iter_backward_search): Make this
|
||||
work.
|
||||
|
||||
* gtk/gtktextbtree.c (gtk_text_btree_new): init stamps to
|
||||
runtime random number different for each tree, instead of
|
||||
a constant I made up.
|
||||
|
||||
Thu Oct 26 07:36:16 2000 Tim Janik <timj@gtk.org>
|
||||
|
||||
* gtk/Makefile.am: buncha cleanups, kludged build sources
|
||||
|
@ -1,3 +1,24 @@
|
||||
2000-10-26 Havoc Pennington <hp@redhat.com>
|
||||
|
||||
* gtk/gtkmarshal.list: add new marshallers used by the text widget
|
||||
|
||||
* gtk/gtktextbuffer.c (gtk_text_buffer_class_init): fix marshaller
|
||||
types
|
||||
|
||||
* gtk/gtktexttagtable.c (gtk_text_tag_table_class_init): fix
|
||||
marshaller types
|
||||
|
||||
* gtk/gtktextlayout.h, gtk/gtktextlayout.c, gtk/gtktextdisplay.h,
|
||||
gtk/gtktextdisplay.c: We need to preserve Tk copyrights and
|
||||
license on these files.
|
||||
|
||||
* gtk/gtktextiter.c (gtk_text_iter_backward_search): Make this
|
||||
work.
|
||||
|
||||
* gtk/gtktextbtree.c (gtk_text_btree_new): init stamps to
|
||||
runtime random number different for each tree, instead of
|
||||
a constant I made up.
|
||||
|
||||
Thu Oct 26 07:36:16 2000 Tim Janik <timj@gtk.org>
|
||||
|
||||
* gtk/Makefile.am: buncha cleanups, kludged build sources
|
||||
|
@ -1,3 +1,24 @@
|
||||
2000-10-26 Havoc Pennington <hp@redhat.com>
|
||||
|
||||
* gtk/gtkmarshal.list: add new marshallers used by the text widget
|
||||
|
||||
* gtk/gtktextbuffer.c (gtk_text_buffer_class_init): fix marshaller
|
||||
types
|
||||
|
||||
* gtk/gtktexttagtable.c (gtk_text_tag_table_class_init): fix
|
||||
marshaller types
|
||||
|
||||
* gtk/gtktextlayout.h, gtk/gtktextlayout.c, gtk/gtktextdisplay.h,
|
||||
gtk/gtktextdisplay.c: We need to preserve Tk copyrights and
|
||||
license on these files.
|
||||
|
||||
* gtk/gtktextiter.c (gtk_text_iter_backward_search): Make this
|
||||
work.
|
||||
|
||||
* gtk/gtktextbtree.c (gtk_text_btree_new): init stamps to
|
||||
runtime random number different for each tree, instead of
|
||||
a constant I made up.
|
||||
|
||||
Thu Oct 26 07:36:16 2000 Tim Janik <timj@gtk.org>
|
||||
|
||||
* gtk/Makefile.am: buncha cleanups, kludged build sources
|
||||
|
@ -1,3 +1,24 @@
|
||||
2000-10-26 Havoc Pennington <hp@redhat.com>
|
||||
|
||||
* gtk/gtkmarshal.list: add new marshallers used by the text widget
|
||||
|
||||
* gtk/gtktextbuffer.c (gtk_text_buffer_class_init): fix marshaller
|
||||
types
|
||||
|
||||
* gtk/gtktexttagtable.c (gtk_text_tag_table_class_init): fix
|
||||
marshaller types
|
||||
|
||||
* gtk/gtktextlayout.h, gtk/gtktextlayout.c, gtk/gtktextdisplay.h,
|
||||
gtk/gtktextdisplay.c: We need to preserve Tk copyrights and
|
||||
license on these files.
|
||||
|
||||
* gtk/gtktextiter.c (gtk_text_iter_backward_search): Make this
|
||||
work.
|
||||
|
||||
* gtk/gtktextbtree.c (gtk_text_btree_new): init stamps to
|
||||
runtime random number different for each tree, instead of
|
||||
a constant I made up.
|
||||
|
||||
Thu Oct 26 07:36:16 2000 Tim Janik <timj@gtk.org>
|
||||
|
||||
* gtk/Makefile.am: buncha cleanups, kludged build sources
|
||||
|
@ -49,11 +49,14 @@ VOID:INT,INT,INT,INT
|
||||
VOID:INT,INT,POINTER
|
||||
VOID:OBJECT
|
||||
VOID:POINTER
|
||||
VOID:POINTER,BOOLEAN
|
||||
VOID:POINTER,INT
|
||||
VOID:POINTER,INT,INT,POINTER,UINT,UINT
|
||||
VOID:POINTER,INT,POINTER
|
||||
VOID:POINTER,POINTER
|
||||
VOID:POINTER,POINTER,BOOLEAN
|
||||
VOID:POINTER,POINTER,INT
|
||||
VOID:POINTER,POINTER,INT,BOOLEAN
|
||||
VOID:POINTER,POINTER,INT,INT
|
||||
VOID:POINTER,POINTER,POINTER
|
||||
VOID:POINTER,POINTER,UINT,UINT
|
||||
|
@ -49,11 +49,14 @@ VOID:INT,INT,INT,INT
|
||||
VOID:INT,INT,POINTER
|
||||
VOID:OBJECT
|
||||
VOID:POINTER
|
||||
VOID:POINTER,BOOLEAN
|
||||
VOID:POINTER,INT
|
||||
VOID:POINTER,INT,INT,POINTER,UINT,UINT
|
||||
VOID:POINTER,INT,POINTER
|
||||
VOID:POINTER,POINTER
|
||||
VOID:POINTER,POINTER,BOOLEAN
|
||||
VOID:POINTER,POINTER,INT
|
||||
VOID:POINTER,POINTER,INT,BOOLEAN
|
||||
VOID:POINTER,POINTER,INT,INT
|
||||
VOID:POINTER,POINTER,POINTER
|
||||
VOID:POINTER,POINTER,UINT,UINT
|
||||
|
@ -394,9 +394,11 @@ gtk_text_btree_new (GtkTextTagTable *table,
|
||||
tree->views = NULL;
|
||||
|
||||
/* Set these to values that are unlikely to be found
|
||||
in random memory garbage. */
|
||||
tree->chars_changed_stamp = 49;
|
||||
tree->segments_changed_stamp = 243;
|
||||
* in random memory garbage, and also avoid
|
||||
* duplicates between tree instances.
|
||||
*/
|
||||
tree->chars_changed_stamp = g_random_int ();
|
||||
tree->segments_changed_stamp = g_random_int ();
|
||||
|
||||
tree->end_iter_line_stamp = tree->chars_changed_stamp - 1;
|
||||
tree->end_iter_line = NULL;
|
||||
|
@ -137,7 +137,7 @@ gtk_text_buffer_class_init (GtkTextBufferClass *klass)
|
||||
GTK_RUN_LAST,
|
||||
GTK_CLASS_TYPE (object_class),
|
||||
GTK_SIGNAL_OFFSET (GtkTextBufferClass, insert_text),
|
||||
gtk_marshal_VOID__POINTER_POINTER_INT_INT,
|
||||
gtk_marshal_VOID__POINTER_POINTER_INT_BOOLEAN,
|
||||
GTK_TYPE_NONE,
|
||||
4,
|
||||
GTK_TYPE_POINTER,
|
||||
@ -150,7 +150,7 @@ gtk_text_buffer_class_init (GtkTextBufferClass *klass)
|
||||
GTK_RUN_LAST,
|
||||
GTK_CLASS_TYPE (object_class),
|
||||
GTK_SIGNAL_OFFSET (GtkTextBufferClass, delete_text),
|
||||
gtk_marshal_VOID__POINTER_POINTER_INT,
|
||||
gtk_marshal_VOID__POINTER_POINTER_BOOLEAN,
|
||||
GTK_TYPE_NONE,
|
||||
3,
|
||||
GTK_TYPE_POINTER,
|
||||
|
@ -5,6 +5,26 @@
|
||||
* Copyright (c) 2000 Red Hat, Inc.
|
||||
* Tk->Gtk port by Havoc Pennington
|
||||
*
|
||||
* This file can be used under your choice of two licenses, the LGPL
|
||||
* and the original Tk license.
|
||||
*
|
||||
* LGPL:
|
||||
*
|
||||
* This library is free software; you can redistribute it and/or
|
||||
* modify it under the terms of the GNU Lesser General Public
|
||||
* License as published by the Free Software Foundation; either
|
||||
* version 2 of the License, or (at your option) any later version.
|
||||
*
|
||||
* This library is distributed in the hope that it will be useful,
|
||||
* but WITHOUT ANY WARRANTY; without even the implied warranty of
|
||||
* MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the GNU
|
||||
* Lesser General Public License for more details.
|
||||
*
|
||||
* You should have received a copy of the GNU Lesser General Public
|
||||
* License along with this library; if not, write to the Free
|
||||
* Software Foundation, Inc., 675 Mass Ave, Cambridge, MA 02139, USA.
|
||||
*
|
||||
* Original Tk license:
|
||||
*
|
||||
* This software is copyrighted by the Regents of the University of
|
||||
* California, Sun Microsystems, Inc., and other parties. The
|
||||
@ -45,7 +65,13 @@
|
||||
* foregoing, the authors grant the U.S. Government and others acting
|
||||
* in its behalf permission to use and distribute the software in
|
||||
* accordance with the terms specified in this license.
|
||||
*
|
||||
*
|
||||
*/
|
||||
/*
|
||||
* Modified by the GTK+ Team and others 1997-2000. See the AUTHORS
|
||||
* file for a list of people on the GTK+ Team. See the ChangeLog
|
||||
* files for a list of changes. These files are distributed with
|
||||
* GTK+ at ftp://ftp.gtk.org/pub/gtk/.
|
||||
*/
|
||||
|
||||
#include "gtktextdisplay.h"
|
||||
|
@ -1,6 +1,15 @@
|
||||
/* GTK - The GIMP Toolkit
|
||||
* Copyright (C) 1995-1997 Peter Mattis, Spencer Kimball and Josh MacDonald
|
||||
/* gtktextdisplay.c - display layed-out text
|
||||
*
|
||||
* Copyright (c) 1992-1994 The Regents of the University of California.
|
||||
* Copyright (c) 1994-1997 Sun Microsystems, Inc.
|
||||
* Copyright (c) 2000 Red Hat, Inc.
|
||||
* Tk->Gtk port by Havoc Pennington
|
||||
*
|
||||
* This file can be used under your choice of two licenses, the LGPL
|
||||
* and the original Tk license.
|
||||
*
|
||||
* LGPL:
|
||||
*
|
||||
* This library is free software; you can redistribute it and/or
|
||||
* modify it under the terms of the GNU Lesser General Public
|
||||
* License as published by the Free Software Foundation; either
|
||||
@ -14,8 +23,50 @@
|
||||
* You should have received a copy of the GNU Lesser General Public
|
||||
* License along with this library; if not, write to the Free
|
||||
* Software Foundation, Inc., 675 Mass Ave, Cambridge, MA 02139, USA.
|
||||
*
|
||||
* Original Tk license:
|
||||
*
|
||||
* This software is copyrighted by the Regents of the University of
|
||||
* California, Sun Microsystems, Inc., and other parties. The
|
||||
* following terms apply to all files associated with the software
|
||||
* unless explicitly disclaimed in individual files.
|
||||
*
|
||||
* The authors hereby grant permission to use, copy, modify,
|
||||
* distribute, and license this software and its documentation for any
|
||||
* purpose, provided that existing copyright notices are retained in
|
||||
* all copies and that this notice is included verbatim in any
|
||||
* distributions. No written agreement, license, or royalty fee is
|
||||
* required for any of the authorized uses. Modifications to this
|
||||
* software may be copyrighted by their authors and need not follow
|
||||
* the licensing terms described here, provided that the new terms are
|
||||
* clearly indicated on the first page of each file where they apply.
|
||||
*
|
||||
* IN NO EVENT SHALL THE AUTHORS OR DISTRIBUTORS BE LIABLE TO ANY
|
||||
* PARTY FOR DIRECT, INDIRECT, SPECIAL, INCIDENTAL, OR CONSEQUENTIAL
|
||||
* DAMAGES ARISING OUT OF THE USE OF THIS SOFTWARE, ITS DOCUMENTATION,
|
||||
* OR ANY DERIVATIVES THEREOF, EVEN IF THE AUTHORS HAVE BEEN ADVISED
|
||||
* OF THE POSSIBILITY OF SUCH DAMAGE.
|
||||
*
|
||||
* THE AUTHORS AND DISTRIBUTORS SPECIFICALLY DISCLAIM ANY WARRANTIES,
|
||||
* INCLUDING, BUT NOT LIMITED TO, THE IMPLIED WARRANTIES OF
|
||||
* MERCHANTABILITY, FITNESS FOR A PARTICULAR PURPOSE, AND
|
||||
* NON-INFRINGEMENT. THIS SOFTWARE IS PROVIDED ON AN "AS IS" BASIS,
|
||||
* AND THE AUTHORS AND DISTRIBUTORS HAVE NO OBLIGATION TO PROVIDE
|
||||
* MAINTENANCE, SUPPORT, UPDATES, ENHANCEMENTS, OR MODIFICATIONS.
|
||||
*
|
||||
* GOVERNMENT USE: If you are acquiring this software on behalf of the
|
||||
* U.S. government, the Government shall have only "Restricted Rights"
|
||||
* in the software and related documentation as defined in the Federal
|
||||
* Acquisition Regulations (FARs) in Clause 52.227.19 (c) (2). If you
|
||||
* are acquiring the software on behalf of the Department of Defense,
|
||||
* the software shall be classified as "Commercial Computer Software"
|
||||
* and the Government shall have only "Restricted Rights" as defined
|
||||
* in Clause 252.227-7013 (c) (1) of DFARs. Notwithstanding the
|
||||
* foregoing, the authors grant the U.S. Government and others acting
|
||||
* in its behalf permission to use and distribute the software in
|
||||
* accordance with the terms specified in this license.
|
||||
*
|
||||
*/
|
||||
|
||||
/*
|
||||
* Modified by the GTK+ Team and others 1997-2000. See the AUTHORS
|
||||
* file for a list of people on the GTK+ Team. See the ChangeLog
|
||||
|
@ -2172,7 +2172,7 @@ gtk_text_iter_backward_line(GtkTextIter *iter)
|
||||
|
||||
check_invariants(iter);
|
||||
|
||||
new_line = gtk_text_line_previous(real->line);
|
||||
new_line = gtk_text_line_previous (real->line);
|
||||
|
||||
offset_will_change = FALSE;
|
||||
if (real->line_char_offset > 0)
|
||||
@ -2182,7 +2182,7 @@ gtk_text_iter_backward_line(GtkTextIter *iter)
|
||||
{
|
||||
real->line = new_line;
|
||||
|
||||
adjust_line_number(real, -1);
|
||||
adjust_line_number (real, -1);
|
||||
}
|
||||
else
|
||||
{
|
||||
@ -2200,19 +2200,18 @@ gtk_text_iter_backward_line(GtkTextIter *iter)
|
||||
|
||||
/* Find first segment in line */
|
||||
real->any_segment = real->line->segments;
|
||||
real->segment = gtk_text_line_byte_to_segment(real->line,
|
||||
0, &offset);
|
||||
real->segment = gtk_text_line_byte_to_segment (real->line,
|
||||
0, &offset);
|
||||
|
||||
g_assert(offset == 0);
|
||||
|
||||
/* Note that if we are on the first line, we snap to the start
|
||||
of the first line and return TRUE, so TRUE means the
|
||||
iterator changed, not that the line changed; this is maybe
|
||||
a bit weird. I'm not sure there's an obvious right thing
|
||||
to do though.
|
||||
*/
|
||||
/* Note that if we are on the first line, we snap to the start of
|
||||
* the first line and return TRUE, so TRUE means the iterator
|
||||
* changed, not that the line changed; this is maybe a bit
|
||||
* weird. I'm not sure there's an obvious right thing to do though.
|
||||
*/
|
||||
|
||||
check_invariants(iter);
|
||||
check_invariants (iter);
|
||||
|
||||
return TRUE;
|
||||
}
|
||||
@ -3048,7 +3047,20 @@ gtk_text_iter_forward_search (const GtkTextIter *iter,
|
||||
g_return_val_if_fail (str != NULL, FALSE);
|
||||
|
||||
if (*str == '\0')
|
||||
return TRUE; /* we found the empty string */
|
||||
{
|
||||
/* If we can move one char, return the empty string there */
|
||||
match = *iter;
|
||||
if (gtk_text_iter_next_char (&match))
|
||||
{
|
||||
if (match_start)
|
||||
*match_start = match;
|
||||
if (match_end)
|
||||
*match_end = match;
|
||||
return TRUE;
|
||||
}
|
||||
else
|
||||
return FALSE;
|
||||
}
|
||||
|
||||
/* locate all lines */
|
||||
|
||||
@ -3085,17 +3097,332 @@ gtk_text_iter_forward_search (const GtkTextIter *iter,
|
||||
return retval;
|
||||
}
|
||||
|
||||
gboolean
|
||||
gtk_text_iter_backward_search (GtkTextIter *iter,
|
||||
const char *str,
|
||||
gboolean visible_only,
|
||||
gboolean slice)
|
||||
static gboolean
|
||||
vectors_equal_ignoring_trailing (gchar **vec1,
|
||||
gchar **vec2)
|
||||
{
|
||||
/* Ignores trailing chars in vec2's last line */
|
||||
|
||||
gchar **i1, **i2;
|
||||
|
||||
i1 = vec1;
|
||||
i2 = vec2;
|
||||
|
||||
while (*i1 && *i2)
|
||||
{
|
||||
if (strcmp (*i1, *i2) != 0)
|
||||
{
|
||||
if (*(i2 + 1) == NULL) /* if this is the last line */
|
||||
{
|
||||
gint len1 = strlen (*i1);
|
||||
gint len2 = strlen (*i2);
|
||||
|
||||
if (len2 >= len1 &&
|
||||
strncmp (*i1, *i2, len1) == 0)
|
||||
{
|
||||
/* We matched ignoring the trailing stuff in vec2 */
|
||||
return TRUE;
|
||||
}
|
||||
else
|
||||
{
|
||||
return FALSE;
|
||||
}
|
||||
}
|
||||
else
|
||||
{
|
||||
return FALSE;
|
||||
}
|
||||
}
|
||||
++i1;
|
||||
++i2;
|
||||
}
|
||||
|
||||
if (*i1 || *i2)
|
||||
{
|
||||
return FALSE;
|
||||
}
|
||||
else
|
||||
return TRUE;
|
||||
}
|
||||
|
||||
typedef struct _LinesWindow LinesWindow;
|
||||
|
||||
struct _LinesWindow
|
||||
{
|
||||
gint n_lines;
|
||||
gchar **lines;
|
||||
GtkTextIter first_line_start;
|
||||
GtkTextIter first_line_end;
|
||||
gboolean slice;
|
||||
gboolean visible_only;
|
||||
};
|
||||
|
||||
static void
|
||||
lines_window_init (LinesWindow *win,
|
||||
const GtkTextIter *start)
|
||||
{
|
||||
gint i;
|
||||
GtkTextIter line_start;
|
||||
GtkTextIter line_end;
|
||||
|
||||
/* If we start on line 1, there are 2 lines to search (0 and 1), so
|
||||
* n_lines can be 2.
|
||||
*/
|
||||
if (gtk_text_iter_is_first (start) ||
|
||||
gtk_text_iter_get_line (start) + 1 < win->n_lines)
|
||||
{
|
||||
/* Already at the end, or not enough lines to match */
|
||||
win->lines = g_new0 (gchar*, 1);
|
||||
*win->lines = NULL;
|
||||
return;
|
||||
}
|
||||
|
||||
line_start = *start;
|
||||
line_end = *start;
|
||||
|
||||
/* Move to start iter to start of line */
|
||||
gtk_text_iter_set_line_offset (&line_start, 0);
|
||||
|
||||
if (gtk_text_iter_equal (&line_start, &line_end))
|
||||
{
|
||||
/* we were already at the start; so go back one line */
|
||||
gtk_text_iter_backward_line (&line_start);
|
||||
}
|
||||
|
||||
win->first_line_start = line_start;
|
||||
win->first_line_end = line_end;
|
||||
|
||||
win->lines = g_new0 (gchar*, win->n_lines + 1);
|
||||
|
||||
i = win->n_lines - 1;
|
||||
while (i >= 0)
|
||||
{
|
||||
gchar *line_text;
|
||||
|
||||
if (win->slice)
|
||||
{
|
||||
if (win->visible_only)
|
||||
line_text = gtk_text_iter_get_visible_slice (&line_start, &line_end);
|
||||
else
|
||||
line_text = gtk_text_iter_get_slice (&line_start, &line_end);
|
||||
}
|
||||
else
|
||||
{
|
||||
if (win->visible_only)
|
||||
line_text = gtk_text_iter_get_visible_text (&line_start, &line_end);
|
||||
else
|
||||
line_text = gtk_text_iter_get_text (&line_start, &line_end);
|
||||
}
|
||||
|
||||
win->lines[i] = line_text;
|
||||
|
||||
line_end = line_start;
|
||||
gtk_text_iter_backward_line (&line_start);
|
||||
|
||||
--i;
|
||||
}
|
||||
}
|
||||
|
||||
static gboolean
|
||||
lines_window_back (LinesWindow *win)
|
||||
{
|
||||
GtkTextIter new_start;
|
||||
gchar *line_text;
|
||||
|
||||
new_start = win->first_line_start;
|
||||
|
||||
if (!gtk_text_iter_backward_line (&new_start))
|
||||
return FALSE;
|
||||
else
|
||||
{
|
||||
win->first_line_start = new_start;
|
||||
win->first_line_end = new_start;
|
||||
|
||||
gtk_text_iter_forward_line (&win->first_line_end);
|
||||
}
|
||||
|
||||
if (win->slice)
|
||||
{
|
||||
if (win->visible_only)
|
||||
line_text = gtk_text_iter_get_visible_slice (&win->first_line_start,
|
||||
&win->first_line_end);
|
||||
else
|
||||
line_text = gtk_text_iter_get_slice (&win->first_line_start,
|
||||
&win->first_line_end);
|
||||
}
|
||||
else
|
||||
{
|
||||
if (win->visible_only)
|
||||
line_text = gtk_text_iter_get_visible_text (&win->first_line_start,
|
||||
&win->first_line_end);
|
||||
else
|
||||
line_text = gtk_text_iter_get_text (&win->first_line_start,
|
||||
&win->first_line_end);
|
||||
}
|
||||
|
||||
/* Move lines to make room for first line. */
|
||||
g_memmove (win->lines + 1, win->lines, win->n_lines * sizeof (gchar*));
|
||||
|
||||
*win->lines = line_text;
|
||||
|
||||
/* Free old last line and NULL-terminate */
|
||||
g_free (win->lines[win->n_lines]);
|
||||
win->lines[win->n_lines] = NULL;
|
||||
|
||||
return TRUE;
|
||||
}
|
||||
|
||||
static void
|
||||
lines_window_free (LinesWindow *win)
|
||||
{
|
||||
g_strfreev (win->lines);
|
||||
}
|
||||
|
||||
static gchar*
|
||||
my_strrstr (const gchar *haystack,
|
||||
const gchar *needle)
|
||||
{
|
||||
/* FIXME GLib should have a nice implementation in it, this
|
||||
* is slow-ass crap.
|
||||
*/
|
||||
|
||||
gint haystack_len = strlen (haystack);
|
||||
gint needle_len = strlen (needle);
|
||||
const gchar *needle_end = needle + needle_len;
|
||||
const gchar *haystack_rend = haystack - 1;
|
||||
const gchar *needle_rend = needle - 1;
|
||||
const gchar *p;
|
||||
|
||||
p = haystack + haystack_len;
|
||||
while (p != haystack)
|
||||
{
|
||||
const gchar *n = needle_end - 1;
|
||||
const gchar *s = p - 1;
|
||||
while (s != haystack_rend &&
|
||||
n != needle_rend &&
|
||||
*s == *n)
|
||||
{
|
||||
--n;
|
||||
--s;
|
||||
}
|
||||
|
||||
if (n == needle_rend)
|
||||
return ++s;
|
||||
|
||||
--p;
|
||||
}
|
||||
|
||||
return NULL;
|
||||
}
|
||||
|
||||
gboolean
|
||||
gtk_text_iter_backward_search (const GtkTextIter *iter,
|
||||
const gchar *str,
|
||||
gboolean visible_only,
|
||||
gboolean slice,
|
||||
GtkTextIter *match_start,
|
||||
GtkTextIter *match_end)
|
||||
{
|
||||
gchar **lines = NULL;
|
||||
gchar **l;
|
||||
gint n_lines;
|
||||
LinesWindow win;
|
||||
gboolean retval = FALSE;
|
||||
|
||||
g_return_val_if_fail (iter != NULL, FALSE);
|
||||
g_return_val_if_fail (str != NULL, FALSE);
|
||||
|
||||
if (*str == '\0')
|
||||
{
|
||||
/* If we can move one char, return the empty string there */
|
||||
GtkTextIter match = *iter;
|
||||
|
||||
if (gtk_text_iter_prev_char (&match))
|
||||
{
|
||||
if (match_start)
|
||||
*match_start = match;
|
||||
if (match_end)
|
||||
*match_end = match;
|
||||
return TRUE;
|
||||
}
|
||||
else
|
||||
return FALSE;
|
||||
}
|
||||
|
||||
/* locate all lines */
|
||||
|
||||
lines = strbreakup (str, "\n", -1);
|
||||
|
||||
l = lines;
|
||||
n_lines = 0;
|
||||
while (*l)
|
||||
{
|
||||
++n_lines;
|
||||
++l;
|
||||
}
|
||||
|
||||
win.n_lines = n_lines;
|
||||
win.slice = slice;
|
||||
win.visible_only = visible_only;
|
||||
|
||||
lines_window_init (&win, iter);
|
||||
|
||||
if (*win.lines == NULL)
|
||||
goto out;
|
||||
|
||||
do
|
||||
{
|
||||
gchar *first_line_match;
|
||||
|
||||
/* If there are multiple lines, the first line will
|
||||
* end in '\n', so this will only match at the
|
||||
* end of the first line, which is correct.
|
||||
*/
|
||||
first_line_match = my_strrstr (*win.lines, *lines);
|
||||
|
||||
if (first_line_match &&
|
||||
vectors_equal_ignoring_trailing (lines + 1, win.lines + 1))
|
||||
{
|
||||
/* Match! */
|
||||
gint offset;
|
||||
GtkTextIter next;
|
||||
|
||||
/* Offset to start of search string */
|
||||
offset = g_utf8_strlen (*win.lines, first_line_match - *win.lines);
|
||||
|
||||
next = win.first_line_start;
|
||||
if (match_start)
|
||||
{
|
||||
*match_start = next;
|
||||
forward_chars_with_skipping (match_start, offset,
|
||||
visible_only, !slice);
|
||||
}
|
||||
|
||||
/* Go to end of search string */
|
||||
l = lines;
|
||||
while (*l)
|
||||
{
|
||||
offset += g_utf8_strlen (*l, -1);
|
||||
++l;
|
||||
}
|
||||
|
||||
forward_chars_with_skipping (&next, offset,
|
||||
visible_only, !slice);
|
||||
|
||||
if (match_end)
|
||||
*match_end = next;
|
||||
|
||||
retval = TRUE;
|
||||
goto out;
|
||||
}
|
||||
}
|
||||
while (lines_window_back (&win));
|
||||
|
||||
out:
|
||||
lines_window_free (&win);
|
||||
g_strfreev (lines);
|
||||
|
||||
return retval;
|
||||
}
|
||||
|
||||
/*
|
||||
@ -3103,7 +3430,8 @@ gtk_text_iter_backward_search (GtkTextIter *iter,
|
||||
*/
|
||||
|
||||
gboolean
|
||||
gtk_text_iter_equal(const GtkTextIter *lhs, const GtkTextIter *rhs)
|
||||
gtk_text_iter_equal (const GtkTextIter *lhs,
|
||||
const GtkTextIter *rhs)
|
||||
{
|
||||
GtkTextRealIter *real_lhs;
|
||||
GtkTextRealIter *real_rhs;
|
||||
|
@ -185,17 +185,20 @@ gboolean gtk_text_iter_backward_find_char (GtkTextIter *iter,
|
||||
GtkTextCharPredicate pred,
|
||||
gpointer user_data);
|
||||
|
||||
gboolean gtk_text_iter_forward_search (const GtkTextIter *iter,
|
||||
const gchar *str,
|
||||
gboolean visible_only,
|
||||
gboolean slice,
|
||||
GtkTextIter *match_start,
|
||||
GtkTextIter *match_end);
|
||||
gboolean gtk_text_iter_forward_search (const GtkTextIter *iter,
|
||||
const gchar *str,
|
||||
gboolean visible_only,
|
||||
gboolean slice,
|
||||
GtkTextIter *match_start,
|
||||
GtkTextIter *match_end);
|
||||
gboolean gtk_text_iter_backward_search (const GtkTextIter *iter,
|
||||
const gchar *str,
|
||||
gboolean visible_only,
|
||||
gboolean slice,
|
||||
GtkTextIter *match_start,
|
||||
GtkTextIter *match_end);
|
||||
|
||||
|
||||
gboolean gtk_text_iter_backward_search (GtkTextIter *iter,
|
||||
const char *str,
|
||||
gboolean visible_only,
|
||||
gboolean slice);
|
||||
|
||||
/*
|
||||
* Comparisons
|
||||
|
@ -1,4 +1,5 @@
|
||||
/* gtktextlayout.c - calculate the layout of the text
|
||||
/* GTK - The GIMP Toolkit
|
||||
* gtktextlayout.c - calculate the layout of the text
|
||||
*
|
||||
* Copyright (c) 1992-1994 The Regents of the University of California.
|
||||
* Copyright (c) 1994-1997 Sun Microsystems, Inc.
|
||||
@ -6,6 +7,26 @@
|
||||
* Tk->Gtk port by Havoc Pennington
|
||||
* Pango support by Owen Taylor
|
||||
*
|
||||
* This file can be used under your choice of two licenses, the LGPL
|
||||
* and the original Tk license.
|
||||
*
|
||||
* LGPL:
|
||||
*
|
||||
* This library is free software; you can redistribute it and/or
|
||||
* modify it under the terms of the GNU Lesser General Public
|
||||
* License as published by the Free Software Foundation; either
|
||||
* version 2 of the License, or (at your option) any later version.
|
||||
*
|
||||
* This library is distributed in the hope that it will be useful,
|
||||
* but WITHOUT ANY WARRANTY; without even the implied warranty of
|
||||
* MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the GNU
|
||||
* Lesser General Public License for more details.
|
||||
*
|
||||
* You should have received a copy of the GNU Lesser General Public
|
||||
* License along with this library; if not, write to the Free
|
||||
* Software Foundation, Inc., 675 Mass Ave, Cambridge, MA 02139, USA.
|
||||
*
|
||||
* Original Tk license:
|
||||
*
|
||||
* This software is copyrighted by the Regents of the University of
|
||||
* California, Sun Microsystems, Inc., and other parties. The
|
||||
@ -46,7 +67,13 @@
|
||||
* foregoing, the authors grant the U.S. Government and others acting
|
||||
* in its behalf permission to use and distribute the software in
|
||||
* accordance with the terms specified in this license.
|
||||
*
|
||||
*
|
||||
*/
|
||||
/*
|
||||
* Modified by the GTK+ Team and others 1997-2000. See the AUTHORS
|
||||
* file for a list of people on the GTK+ Team. See the ChangeLog
|
||||
* files for a list of changes. These files are distributed with
|
||||
* GTK+ at ftp://ftp.gtk.org/pub/gtk/.
|
||||
*/
|
||||
|
||||
#include "gtksignal.h"
|
||||
|
@ -1,6 +1,17 @@
|
||||
/* GTK - The GIMP Toolkit
|
||||
* Copyright (C) 1995-1997 Peter Mattis, Spencer Kimball and Josh MacDonald
|
||||
* gtktextlayout.h
|
||||
*
|
||||
* Copyright (c) 1992-1994 The Regents of the University of California.
|
||||
* Copyright (c) 1994-1997 Sun Microsystems, Inc.
|
||||
* Copyright (c) 2000 Red Hat, Inc.
|
||||
* Tk->Gtk port by Havoc Pennington
|
||||
* Pango support by Owen Taylor
|
||||
*
|
||||
* This file can be used under your choice of two licenses, the LGPL
|
||||
* and the original Tk license.
|
||||
*
|
||||
* LGPL:
|
||||
*
|
||||
* This library is free software; you can redistribute it and/or
|
||||
* modify it under the terms of the GNU Lesser General Public
|
||||
* License as published by the Free Software Foundation; either
|
||||
@ -14,8 +25,50 @@
|
||||
* You should have received a copy of the GNU Lesser General Public
|
||||
* License along with this library; if not, write to the Free
|
||||
* Software Foundation, Inc., 675 Mass Ave, Cambridge, MA 02139, USA.
|
||||
*
|
||||
* Original Tk license:
|
||||
*
|
||||
* This software is copyrighted by the Regents of the University of
|
||||
* California, Sun Microsystems, Inc., and other parties. The
|
||||
* following terms apply to all files associated with the software
|
||||
* unless explicitly disclaimed in individual files.
|
||||
*
|
||||
* The authors hereby grant permission to use, copy, modify,
|
||||
* distribute, and license this software and its documentation for any
|
||||
* purpose, provided that existing copyright notices are retained in
|
||||
* all copies and that this notice is included verbatim in any
|
||||
* distributions. No written agreement, license, or royalty fee is
|
||||
* required for any of the authorized uses. Modifications to this
|
||||
* software may be copyrighted by their authors and need not follow
|
||||
* the licensing terms described here, provided that the new terms are
|
||||
* clearly indicated on the first page of each file where they apply.
|
||||
*
|
||||
* IN NO EVENT SHALL THE AUTHORS OR DISTRIBUTORS BE LIABLE TO ANY
|
||||
* PARTY FOR DIRECT, INDIRECT, SPECIAL, INCIDENTAL, OR CONSEQUENTIAL
|
||||
* DAMAGES ARISING OUT OF THE USE OF THIS SOFTWARE, ITS DOCUMENTATION,
|
||||
* OR ANY DERIVATIVES THEREOF, EVEN IF THE AUTHORS HAVE BEEN ADVISED
|
||||
* OF THE POSSIBILITY OF SUCH DAMAGE.
|
||||
*
|
||||
* THE AUTHORS AND DISTRIBUTORS SPECIFICALLY DISCLAIM ANY WARRANTIES,
|
||||
* INCLUDING, BUT NOT LIMITED TO, THE IMPLIED WARRANTIES OF
|
||||
* MERCHANTABILITY, FITNESS FOR A PARTICULAR PURPOSE, AND
|
||||
* NON-INFRINGEMENT. THIS SOFTWARE IS PROVIDED ON AN "AS IS" BASIS,
|
||||
* AND THE AUTHORS AND DISTRIBUTORS HAVE NO OBLIGATION TO PROVIDE
|
||||
* MAINTENANCE, SUPPORT, UPDATES, ENHANCEMENTS, OR MODIFICATIONS.
|
||||
*
|
||||
* GOVERNMENT USE: If you are acquiring this software on behalf of the
|
||||
* U.S. government, the Government shall have only "Restricted Rights"
|
||||
* in the software and related documentation as defined in the Federal
|
||||
* Acquisition Regulations (FARs) in Clause 52.227.19 (c) (2). If you
|
||||
* are acquiring the software on behalf of the Department of Defense,
|
||||
* the software shall be classified as "Commercial Computer Software"
|
||||
* and the Government shall have only "Restricted Rights" as defined
|
||||
* in Clause 252.227-7013 (c) (1) of DFARs. Notwithstanding the
|
||||
* foregoing, the authors grant the U.S. Government and others acting
|
||||
* in its behalf permission to use and distribute the software in
|
||||
* accordance with the terms specified in this license.
|
||||
*
|
||||
*/
|
||||
|
||||
/*
|
||||
* Modified by the GTK+ Team and others 1997-2000. See the AUTHORS
|
||||
* file for a list of people on the GTK+ Team. See the ChangeLog
|
||||
|
@ -63,7 +63,7 @@ gtk_text_tag_table_class_init (GtkTextTagTableClass *klass)
|
||||
GTK_RUN_LAST,
|
||||
GTK_CLASS_TYPE (object_class),
|
||||
GTK_SIGNAL_OFFSET (GtkTextTagTableClass, tag_changed),
|
||||
gtk_marshal_VOID__POINTER_INT,
|
||||
gtk_marshal_VOID__POINTER_BOOLEAN,
|
||||
GTK_TYPE_NONE,
|
||||
2,
|
||||
GTK_TYPE_OBJECT,
|
||||
|
@ -835,7 +835,7 @@ set_adjustment_clamped (GtkAdjustment *adj, gfloat val)
|
||||
gtk_adjustment_set_value (adj, val);
|
||||
}
|
||||
|
||||
gboolean
|
||||
static gboolean
|
||||
gtk_text_view_scroll_to_mark_adjusted (GtkTextView *text_view,
|
||||
GtkTextMark *mark,
|
||||
gint margin,
|
||||
|
@ -47,6 +47,9 @@ static void buffer_filename_set (Buffer *buffer);
|
||||
static void buffer_search_forward (Buffer *buffer,
|
||||
const char *str,
|
||||
View *view);
|
||||
static void buffer_search_backward (Buffer *buffer,
|
||||
const char *str,
|
||||
View *view);
|
||||
|
||||
static View *view_from_widget (GtkWidget *widget);
|
||||
|
||||
@ -930,6 +933,12 @@ do_apply_tabs (gpointer callback_data,
|
||||
}
|
||||
}
|
||||
|
||||
enum
|
||||
{
|
||||
RESPONSE_FORWARD,
|
||||
RESPONSE_BACKWARD
|
||||
};
|
||||
|
||||
static void
|
||||
dialog_response_callback (GtkWidget *dialog, gint response_id, gpointer data)
|
||||
{
|
||||
@ -937,6 +946,13 @@ dialog_response_callback (GtkWidget *dialog, gint response_id, gpointer data)
|
||||
View *view = data;
|
||||
GtkTextIter start, end;
|
||||
gchar *search_string;
|
||||
|
||||
if (response_id != RESPONSE_FORWARD &&
|
||||
response_id != RESPONSE_BACKWARD)
|
||||
{
|
||||
gtk_widget_destroy (dialog);
|
||||
return;
|
||||
}
|
||||
|
||||
buffer = gtk_object_get_data (GTK_OBJECT (dialog), "buffer");
|
||||
|
||||
@ -948,9 +964,12 @@ dialog_response_callback (GtkWidget *dialog, gint response_id, gpointer data)
|
||||
search_string = gtk_text_iter_get_text (&start, &end);
|
||||
|
||||
printf ("Searching for `%s'\n", search_string);
|
||||
|
||||
buffer_search_forward (view->buffer, search_string, view);
|
||||
|
||||
if (response_id == RESPONSE_FORWARD)
|
||||
buffer_search_forward (view->buffer, search_string, view);
|
||||
else if (response_id == RESPONSE_BACKWARD)
|
||||
buffer_search_backward (view->buffer, search_string, view);
|
||||
|
||||
g_free (search_string);
|
||||
|
||||
gtk_widget_destroy (dialog);
|
||||
@ -969,7 +988,9 @@ do_search (gpointer callback_data,
|
||||
dialog = gtk_dialog_new_with_buttons ("Search",
|
||||
GTK_WINDOW (view->window),
|
||||
GTK_DIALOG_DESTROY_WITH_PARENT,
|
||||
GTK_STOCK_BUTTON_CLOSE,
|
||||
"Forward", RESPONSE_FORWARD,
|
||||
"Backward", RESPONSE_BACKWARD,
|
||||
GTK_STOCK_BUTTON_CANCEL,
|
||||
GTK_RESPONSE_NONE, NULL);
|
||||
|
||||
|
||||
@ -1303,8 +1324,10 @@ buffer_filename_set (Buffer *buffer)
|
||||
}
|
||||
|
||||
static void
|
||||
buffer_search_forward (Buffer *buffer, const char *str,
|
||||
View *view)
|
||||
buffer_search (Buffer *buffer,
|
||||
const char *str,
|
||||
View *view,
|
||||
gboolean forward)
|
||||
{
|
||||
GtkTextIter iter;
|
||||
GtkTextIter start, end;
|
||||
@ -1324,15 +1347,30 @@ buffer_search_forward (Buffer *buffer, const char *str,
|
||||
if (*str != '\0')
|
||||
{
|
||||
GtkTextIter match_start, match_end;
|
||||
|
||||
while (gtk_text_iter_forward_search (&iter, str, TRUE, FALSE,
|
||||
&match_start, &match_end))
|
||||
{
|
||||
++i;
|
||||
gtk_text_buffer_apply_tag (buffer->buffer, buffer->found_text_tag,
|
||||
&match_start, &match_end);
|
||||
|
||||
iter = match_end;
|
||||
if (forward)
|
||||
{
|
||||
while (gtk_text_iter_forward_search (&iter, str, TRUE, FALSE,
|
||||
&match_start, &match_end))
|
||||
{
|
||||
++i;
|
||||
gtk_text_buffer_apply_tag (buffer->buffer, buffer->found_text_tag,
|
||||
&match_start, &match_end);
|
||||
|
||||
iter = match_end;
|
||||
}
|
||||
}
|
||||
else
|
||||
{
|
||||
while (gtk_text_iter_backward_search (&iter, str, TRUE, FALSE,
|
||||
&match_start, &match_end))
|
||||
{
|
||||
++i;
|
||||
gtk_text_buffer_apply_tag (buffer->buffer, buffer->found_text_tag,
|
||||
&match_start, &match_end);
|
||||
|
||||
iter = match_start;
|
||||
}
|
||||
}
|
||||
}
|
||||
|
||||
@ -1351,6 +1389,20 @@ buffer_search_forward (Buffer *buffer, const char *str,
|
||||
gtk_widget_show (dialog);
|
||||
}
|
||||
|
||||
static void
|
||||
buffer_search_forward (Buffer *buffer, const char *str,
|
||||
View *view)
|
||||
{
|
||||
buffer_search (buffer, str, view, TRUE);
|
||||
}
|
||||
|
||||
static void
|
||||
buffer_search_backward (Buffer *buffer, const char *str,
|
||||
View *view)
|
||||
{
|
||||
buffer_search (buffer, str, view, FALSE);
|
||||
}
|
||||
|
||||
static void
|
||||
buffer_ref (Buffer *buffer)
|
||||
{
|
||||
|
@ -47,6 +47,9 @@ static void buffer_filename_set (Buffer *buffer);
|
||||
static void buffer_search_forward (Buffer *buffer,
|
||||
const char *str,
|
||||
View *view);
|
||||
static void buffer_search_backward (Buffer *buffer,
|
||||
const char *str,
|
||||
View *view);
|
||||
|
||||
static View *view_from_widget (GtkWidget *widget);
|
||||
|
||||
@ -930,6 +933,12 @@ do_apply_tabs (gpointer callback_data,
|
||||
}
|
||||
}
|
||||
|
||||
enum
|
||||
{
|
||||
RESPONSE_FORWARD,
|
||||
RESPONSE_BACKWARD
|
||||
};
|
||||
|
||||
static void
|
||||
dialog_response_callback (GtkWidget *dialog, gint response_id, gpointer data)
|
||||
{
|
||||
@ -937,6 +946,13 @@ dialog_response_callback (GtkWidget *dialog, gint response_id, gpointer data)
|
||||
View *view = data;
|
||||
GtkTextIter start, end;
|
||||
gchar *search_string;
|
||||
|
||||
if (response_id != RESPONSE_FORWARD &&
|
||||
response_id != RESPONSE_BACKWARD)
|
||||
{
|
||||
gtk_widget_destroy (dialog);
|
||||
return;
|
||||
}
|
||||
|
||||
buffer = gtk_object_get_data (GTK_OBJECT (dialog), "buffer");
|
||||
|
||||
@ -948,9 +964,12 @@ dialog_response_callback (GtkWidget *dialog, gint response_id, gpointer data)
|
||||
search_string = gtk_text_iter_get_text (&start, &end);
|
||||
|
||||
printf ("Searching for `%s'\n", search_string);
|
||||
|
||||
buffer_search_forward (view->buffer, search_string, view);
|
||||
|
||||
if (response_id == RESPONSE_FORWARD)
|
||||
buffer_search_forward (view->buffer, search_string, view);
|
||||
else if (response_id == RESPONSE_BACKWARD)
|
||||
buffer_search_backward (view->buffer, search_string, view);
|
||||
|
||||
g_free (search_string);
|
||||
|
||||
gtk_widget_destroy (dialog);
|
||||
@ -969,7 +988,9 @@ do_search (gpointer callback_data,
|
||||
dialog = gtk_dialog_new_with_buttons ("Search",
|
||||
GTK_WINDOW (view->window),
|
||||
GTK_DIALOG_DESTROY_WITH_PARENT,
|
||||
GTK_STOCK_BUTTON_CLOSE,
|
||||
"Forward", RESPONSE_FORWARD,
|
||||
"Backward", RESPONSE_BACKWARD,
|
||||
GTK_STOCK_BUTTON_CANCEL,
|
||||
GTK_RESPONSE_NONE, NULL);
|
||||
|
||||
|
||||
@ -1303,8 +1324,10 @@ buffer_filename_set (Buffer *buffer)
|
||||
}
|
||||
|
||||
static void
|
||||
buffer_search_forward (Buffer *buffer, const char *str,
|
||||
View *view)
|
||||
buffer_search (Buffer *buffer,
|
||||
const char *str,
|
||||
View *view,
|
||||
gboolean forward)
|
||||
{
|
||||
GtkTextIter iter;
|
||||
GtkTextIter start, end;
|
||||
@ -1324,15 +1347,30 @@ buffer_search_forward (Buffer *buffer, const char *str,
|
||||
if (*str != '\0')
|
||||
{
|
||||
GtkTextIter match_start, match_end;
|
||||
|
||||
while (gtk_text_iter_forward_search (&iter, str, TRUE, FALSE,
|
||||
&match_start, &match_end))
|
||||
{
|
||||
++i;
|
||||
gtk_text_buffer_apply_tag (buffer->buffer, buffer->found_text_tag,
|
||||
&match_start, &match_end);
|
||||
|
||||
iter = match_end;
|
||||
if (forward)
|
||||
{
|
||||
while (gtk_text_iter_forward_search (&iter, str, TRUE, FALSE,
|
||||
&match_start, &match_end))
|
||||
{
|
||||
++i;
|
||||
gtk_text_buffer_apply_tag (buffer->buffer, buffer->found_text_tag,
|
||||
&match_start, &match_end);
|
||||
|
||||
iter = match_end;
|
||||
}
|
||||
}
|
||||
else
|
||||
{
|
||||
while (gtk_text_iter_backward_search (&iter, str, TRUE, FALSE,
|
||||
&match_start, &match_end))
|
||||
{
|
||||
++i;
|
||||
gtk_text_buffer_apply_tag (buffer->buffer, buffer->found_text_tag,
|
||||
&match_start, &match_end);
|
||||
|
||||
iter = match_start;
|
||||
}
|
||||
}
|
||||
}
|
||||
|
||||
@ -1351,6 +1389,20 @@ buffer_search_forward (Buffer *buffer, const char *str,
|
||||
gtk_widget_show (dialog);
|
||||
}
|
||||
|
||||
static void
|
||||
buffer_search_forward (Buffer *buffer, const char *str,
|
||||
View *view)
|
||||
{
|
||||
buffer_search (buffer, str, view, TRUE);
|
||||
}
|
||||
|
||||
static void
|
||||
buffer_search_backward (Buffer *buffer, const char *str,
|
||||
View *view)
|
||||
{
|
||||
buffer_search (buffer, str, view, FALSE);
|
||||
}
|
||||
|
||||
static void
|
||||
buffer_ref (Buffer *buffer)
|
||||
{
|
||||
|
Reference in New Issue
Block a user