--- /dev/null
+Index: vte/ChangeLog
+===================================================================
+RCS file: /cvs/gnome/vte/ChangeLog,v
+retrieving revision 1.524
+diff -u -p -r1.524 ChangeLog
+--- vte/ChangeLog 2 May 2004 06:43:01 -0000 1.524
++++ vte/ChangeLog 6 May 2004 08:11:36 -0000
+@@ -1,3 +1,22 @@
++2004-05-06 Padraig O'Briain <padraig.obriain@sun.com>
++ * src/vte.c, src/vteint.h:
++ Add new functions to support accessible text selection:
++ _vte_terminal_get_selection, _vte_terminal_get_start_selection,
++ _vte_terminal_get_end_selection, _vte_terminal_select_text,
++ _vte_terminal_remove_selection
++ * src/vteaccess.c:
++ (xy_from_offset): Fix for offset being entire text.
++ (vte_terminal_accessibility_selection_changed): VteTerminal's
++ selection-changed signal handler which emits text-selection-changed
++ signal.
++ (vte_terminal_accessible_initialize): Connect to VteTerminal's
++ selection-changed signal.
++ (vte_terminal_accessible_get_n_selections) Add implementation.
++ (vte_terminal_accessible_get_selection) Add implementation.
++ (vte_terminal_accessible_add_selection) Add implementation.
++ (vte_terminal_accessible_remove_selection) Add implementation.
++ (vte_terminal_accessible_set_selection) Add implementation.
++
+ 2004-05-02 nalin
+ * src/reaper.c(vte_reaper_add_child): pass the global reaper in as
+ data when adding the child source, not the terminal which called us.
+Index: vte/src/vte.c
+===================================================================
+RCS file: /cvs/gnome/vte/src/vte.c,v
+retrieving revision 1.404
+diff -u -p -r1.404 vte.c
+--- vte/src/vte.c 2 May 2004 06:43:01 -0000 1.404
++++ vte/src/vte.c 6 May 2004 08:11:37 -0000
+@@ -15758,3 +15758,76 @@ _vte_terminal_accessible_ref(VteTerminal
+ g_return_if_fail(VTE_IS_TERMINAL(terminal));
+ terminal->pvt->accessible_emit = TRUE;
+ }
++
++char *
++_vte_terminal_get_selection(VteTerminal *terminal)
++{
++ g_return_val_if_fail(VTE_IS_TERMINAL(terminal), NULL);
++
++ return g_strdup (terminal->pvt->selection);
++}
++
++void
++_vte_terminal_get_start_selection(VteTerminal *terminal, long *x, long *y)
++{
++ struct selection_cell_coords ss;
++
++ g_return_if_fail(VTE_IS_TERMINAL(terminal));
++
++ ss = terminal->pvt->selection_start;
++
++ if (x) {
++ *x = ss.x;
++ }
++
++ if (y) {
++ *y = ss.y;
++ }
++}
++
++void
++_vte_terminal_get_end_selection(VteTerminal *terminal, long *x, long *y)
++{
++ struct selection_cell_coords se;
++
++ g_return_if_fail(VTE_IS_TERMINAL(terminal));
++
++ se = terminal->pvt->selection_end;
++
++ if (x) {
++ *x = se.x;
++ }
++
++ if (y) {
++ *y = se.y;
++ }
++}
++
++void
++_vte_terminal_select_text(VteTerminal *terminal, long start_x, long start_y, long end_x, long end_y, int start_offset, int end_offset)
++{
++ g_return_if_fail(VTE_IS_TERMINAL(terminal));
++
++ terminal->pvt->selection_type = selection_type_char;
++ terminal->pvt->has_selection = TRUE;
++ terminal->pvt->selecting_had_delta = TRUE;
++ terminal->pvt->selection_start.x = start_x;
++ terminal->pvt->selection_start.y = start_y;
++ terminal->pvt->selection_end.x = end_x;
++ terminal->pvt->selection_end.y = end_y;
++ vte_terminal_copy(terminal,
++ GDK_SELECTION_PRIMARY);
++ vte_invalidate_cells (terminal,
++ 0,
++ terminal->column_count,
++ MIN (start_y, end_y),
++ ABS (start_y - end_y) + 1);
++
++ vte_terminal_emit_selection_changed(terminal);
++}
++
++void
++_vte_terminal_remove_selection(VteTerminal *terminal)
++{
++ vte_terminal_deselect_all (terminal);
++}
+Index: vte/src/vteaccess.c
+===================================================================
+RCS file: /cvs/gnome/vte/src/vteaccess.c,v
+retrieving revision 1.44
+diff -u -p -r1.44 vteaccess.c
+--- vte/src/vteaccess.c 1 May 2004 07:12:51 -0000 1.44
++++ vte/src/vteaccess.c 6 May 2004 08:11:37 -0000
+@@ -150,7 +150,7 @@ xy_from_offset (VteTerminalAccessiblePri
+ }
+ }
+ if (i == priv->snapshot_linebreaks->len) {
+- if (offset < priv->snapshot_characters->len) {
++ if (offset <= priv->snapshot_characters->len) {
+ cur_x = offset - cur_offset;
+ cur_y = i - 1;
+ }
+@@ -735,6 +735,16 @@ vte_terminal_accessible_visibility_notif
+ }
+
+ static void
++vte_terminal_accessible_selection_changed (VteTerminal *terminal,
++ gpointer data)
++{
++ g_return_if_fail(VTE_IS_TERMINAL_ACCESSIBLE(data));
++ g_return_if_fail(VTE_IS_TERMINAL(terminal));
++
++ g_signal_emit_by_name (data, "text_selection_changed");
++}
++
++static void
+ vte_terminal_initialize (AtkObject *obj, gpointer data)
+ {
+ VteTerminal *terminal;
+@@ -777,6 +787,9 @@ vte_terminal_initialize (AtkObject *obj,
+ g_signal_connect(G_OBJECT(terminal), "visibility-notify-event",
+ GTK_SIGNAL_FUNC(vte_terminal_accessible_visibility_notify),
+ obj);
++ g_signal_connect(G_OBJECT(terminal), "selection-changed",
++ GTK_SIGNAL_FUNC(vte_terminal_accessible_selection_changed),
++ obj);
+
+ if (GTK_IS_WIDGET((GTK_WIDGET(terminal))->parent)) {
+ parent = gtk_widget_get_accessible((GTK_WIDGET(terminal))->parent);
+@@ -1382,55 +1395,136 @@ vte_terminal_accessible_get_offset_at_po
+ static gint
+ vte_terminal_accessible_get_n_selections(AtkText *text)
+ {
+- g_return_val_if_fail(VTE_IS_TERMINAL_ACCESSIBLE(text), 0);
++ GtkWidget *widget;
++ VteTerminal *terminal;
++
++ g_return_val_if_fail(VTE_IS_TERMINAL_ACCESSIBLE(text), -1);
+ vte_terminal_accessible_update_private_data_if_needed(ATK_OBJECT(text),
+ NULL, NULL);
+- /* FIXME? */
+- return 0;
++
++ widget = GTK_ACCESSIBLE(text)->widget;
++ if (widget == NULL) {
++ /* State is defunct */
++ return -1;
++ }
++ g_return_val_if_fail (VTE_IS_TERMINAL (widget), -1);
++ terminal = VTE_TERMINAL (widget);
++ return (vte_terminal_get_has_selection (terminal)) ? 1 : 0;
+ }
+
+ static gchar *
+ vte_terminal_accessible_get_selection(AtkText *text, gint selection_number,
+ gint *start_offset, gint *end_offset)
+ {
++ GtkWidget *widget;
++ VteTerminal *terminal;
++ VteTerminalAccessiblePrivate *priv;
++ long start_x, start_y, end_x, end_y;
++
+ g_return_val_if_fail(VTE_IS_TERMINAL_ACCESSIBLE(text), NULL);
+ vte_terminal_accessible_update_private_data_if_needed(ATK_OBJECT(text),
+ NULL, NULL);
+- /* FIXME? */
+- return NULL;
++ widget = GTK_ACCESSIBLE(text)->widget;
++ if (widget == NULL) {
++ /* State is defunct */
++ return NULL;
++ }
++ g_return_val_if_fail (VTE_IS_TERMINAL (widget), NULL);
++ terminal = VTE_TERMINAL (widget);
++ if (!vte_terminal_get_has_selection (terminal)) {
++ return NULL;
++ }
++ if (selection_number != 0) {
++ return NULL;
++ }
++
++ priv = g_object_get_data(G_OBJECT(text),
++ VTE_TERMINAL_ACCESSIBLE_PRIVATE_DATA);
++ _vte_terminal_get_start_selection (terminal, &start_x, &start_y);
++ *start_offset = offset_from_xy (priv, start_x, start_y);
++ _vte_terminal_get_end_selection (terminal, &end_x, &end_y);
++ *end_offset = offset_from_xy (priv, end_x, end_y);
++ return _vte_terminal_get_selection (terminal);
+ }
+
+ static gboolean
+ vte_terminal_accessible_add_selection(AtkText *text,
+ gint start_offset, gint end_offset)
+ {
++ GtkWidget *widget;
++ VteTerminal *terminal;
++ VteTerminalAccessiblePrivate *priv;
++ gint start_x, start_y, end_x, end_y;
++
+ g_return_val_if_fail(VTE_IS_TERMINAL_ACCESSIBLE(text), FALSE);
+ vte_terminal_accessible_update_private_data_if_needed(ATK_OBJECT(text),
+ NULL, NULL);
+- /* FIXME? */
+- return FALSE;
++ widget = GTK_ACCESSIBLE(text)->widget;
++ if (widget == NULL) {
++ /* State is defunct */
++ return FALSE;
++ }
++ g_return_val_if_fail (VTE_IS_TERMINAL (widget), FALSE);
++ terminal = VTE_TERMINAL (widget);
++ g_return_val_if_fail (!vte_terminal_get_has_selection (terminal), FALSE);
++ priv = g_object_get_data(G_OBJECT(text),
++ VTE_TERMINAL_ACCESSIBLE_PRIVATE_DATA);
++ xy_from_offset (priv, start_offset, &start_x, &start_y);
++ xy_from_offset (priv, end_offset, &end_x, &end_y);
++ _vte_terminal_select_text (terminal, start_x, start_y, end_x, end_y, start_offset, end_offset);
++ return TRUE;
+ }
+
+ static gboolean
+ vte_terminal_accessible_remove_selection(AtkText *text,
+ gint selection_number)
+ {
++ GtkWidget *widget;
++ VteTerminal *terminal;
++
+ g_return_val_if_fail(VTE_IS_TERMINAL_ACCESSIBLE(text), FALSE);
+ vte_terminal_accessible_update_private_data_if_needed(ATK_OBJECT(text),
+ NULL, NULL);
+- /* FIXME? */
+- return FALSE;
++ widget = GTK_ACCESSIBLE(text)->widget;
++ if (widget == NULL) {
++ /* State is defunct */
++ return FALSE;
++ }
++ g_return_val_if_fail (VTE_IS_TERMINAL (widget), FALSE);
++ terminal = VTE_TERMINAL (widget);
++ if (selection_number == 0 && vte_terminal_get_has_selection (terminal)) {
++ _vte_terminal_remove_selection (terminal);
++ return TRUE;
++ } else {
++ return FALSE;
++ }
+ }
+
+ static gboolean
+ vte_terminal_accessible_set_selection(AtkText *text, gint selection_number,
+ gint start_offset, gint end_offset)
+ {
++ GtkWidget *widget;
++ VteTerminal *terminal;
++
+ g_return_val_if_fail(VTE_IS_TERMINAL_ACCESSIBLE(text), FALSE);
+ vte_terminal_accessible_update_private_data_if_needed(ATK_OBJECT(text),
+ NULL, NULL);
+- /* FIXME? */
+- return FALSE;
++ widget = GTK_ACCESSIBLE(text)->widget;
++ if (widget == NULL) {
++ /* State is defunct */
++ return FALSE;
++ }
++ g_return_val_if_fail (VTE_IS_TERMINAL (widget), FALSE);
++ terminal = VTE_TERMINAL (widget);
++ if (selection_number != 0) {
++ return FALSE;
++ }
++ if (vte_terminal_get_has_selection (terminal)) {
++ _vte_terminal_remove_selection (terminal);
++ }
++
++ return vte_terminal_accessible_add_selection (text, start_offset, end_offset);
+ }
+
+ static gboolean
+@@ -1519,6 +1613,9 @@ vte_terminal_accessible_get_position(Atk
+ *x = 0;
+ *y = 0;
+ widget = (GTK_ACCESSIBLE(component))->widget;
++ if (widget == NULL) {
++ return;
++ }
+ if (!GTK_WIDGET_REALIZED(widget)) {
+ return;
+ }
+@@ -1543,6 +1640,9 @@ vte_terminal_accessible_get_size(AtkComp
+ *width = 0;
+ *height = 0;
+ widget = (GTK_ACCESSIBLE(component))->widget;
++ if (widget == NULL) {
++ return;
++ }
+ if (!GTK_WIDGET_REALIZED(widget)) {
+ return;
+ }
+@@ -1575,7 +1675,12 @@ vte_terminal_accessible_set_size(AtkComp
+ {
+ VteTerminal *terminal;
+ gint columns, rows, xpad, ypad;
+- terminal = VTE_TERMINAL((GTK_ACCESSIBLE(component))->widget);
++ GtkWidget *widget;
++ widget = GTK_ACCESSIBLE(component)->widget;
++ if (widget == NULL) {
++ return FALSE;
++ }
++ terminal = VTE_TERMINAL(widget);
+ vte_terminal_get_padding(terminal, &xpad, &ypad);
+ /* If the size is an exact multiple of the cell size, use that,
+ * otherwise round down. */
+@@ -1599,6 +1704,9 @@ vte_terminal_accessible_grab_focus(AtkCo
+ {
+ GtkWidget *widget;
+ widget = (GTK_ACCESSIBLE(component))->widget;
++ if (widget == NULL) {
++ return FALSE;
++ }
+ if (GTK_WIDGET_HAS_FOCUS(widget)) {
+ return TRUE;
+ }
+Index: vte/src/vteint.h
+===================================================================
+RCS file: /cvs/gnome/vte/src/vteint.h,v
+retrieving revision 1.1
+diff -u -p -r1.1 vteint.h
+--- vte/src/vteint.h 16 Jun 2003 21:16:33 -0000 1.1
++++ vte/src/vteint.h 6 May 2004 08:11:37 -0000
+@@ -26,6 +26,11 @@
+ G_BEGIN_DECLS
+
+ void _vte_terminal_accessible_ref(VteTerminal *terminal);
++char* _vte_terminal_get_selection(VteTerminal *terminal);
++void _vte_terminal_get_start_selection(VteTerminal *terminal, long *x, long *y);
++void _vte_terminal_get_end_selection(VteTerminal *terminal, long *x, long *y);
++void _vte_terminal_select_text(VteTerminal *terminal, long start_x, long start_y, long end_x, long end_y, int start_offset, int end_offset);
++void _vte_terminal_remove_selection(VteTerminal *terminal);
+
+ G_END_DECLS
+