/* This file is part of the GtkHTML library. * * Copyright 2002 Ximian, Inc. * * Author: Radek Doulik * * * This library is free software; you can redistribute it and/or * modify it under the terms of the GNU Library 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 * Library General Public License for more details. * * You should have received a copy of the GNU Library General Public License * along with this library; see the file COPYING.LIB. If not, write to * the Free Software Foundation, Inc., 51 Franklin Street, Fifth Floor, * Boston, MA 02110-1301, USA. */ #include #include #include "htmltext.h" #include "object.h" #include "html.h" #include "hyperlink.h" static void html_a11y_hyper_link_class_init (HTMLA11YHyperLinkClass *klass); static void html_a11y_hyper_link_init (HTMLA11YHyperLink *a11y_hyper_link); static void atk_action_interface_init (AtkActionIface *iface); static gboolean html_a11y_hyper_link_do_action (AtkAction *action, gint i); static gint html_a11y_hyper_link_get_n_actions (AtkAction *action); static G_CONST_RETURN gchar * html_a11y_hyper_link_get_description (AtkAction *action, gint i); static G_CONST_RETURN gchar * html_a11y_hyper_link_get_name (AtkAction *action, gint i); static gboolean html_a11y_hyper_link_set_description (AtkAction *action, gint i, const gchar *description); static AtkObjectClass *parent_class = NULL; GType html_a11y_hyper_link_get_type (void) { static GType type = 0; if (!type) { static const GTypeInfo tinfo = { sizeof (HTMLA11YHyperLinkClass), NULL, /* base init */ NULL, /* base finalize */ (GClassInitFunc) html_a11y_hyper_link_class_init, /* class init */ NULL, /* class finalize */ NULL, /* class data */ sizeof (HTMLA11YHyperLink), /* instance size */ 0, /* nb preallocs */ (GInstanceInitFunc) html_a11y_hyper_link_init, /* instance init */ NULL /* value table */ }; static const GInterfaceInfo atk_action_info = { (GInterfaceInitFunc) atk_action_interface_init, (GInterfaceFinalizeFunc) NULL, NULL }; type = g_type_register_static (ATK_TYPE_HYPERLINK, "HTMLA11YHyperLink", &tinfo, 0); g_type_add_interface_static (type, ATK_TYPE_ACTION, &atk_action_info); } return type; } static void atk_action_interface_init (AtkActionIface *iface) { g_return_if_fail (iface != NULL); iface->do_action = html_a11y_hyper_link_do_action; iface->get_n_actions = html_a11y_hyper_link_get_n_actions; iface->get_description = html_a11y_hyper_link_get_description; iface->get_name = html_a11y_hyper_link_get_name; iface->set_description = html_a11y_hyper_link_set_description; } static void html_a11y_hyper_link_finalize (GObject *obj) { HTMLA11YHyperLink *hl = HTML_A11Y_HYPER_LINK (obj); if (hl->a11y.object) g_object_remove_weak_pointer (G_OBJECT (hl->a11y.object), &hl->a11y.weakref); G_OBJECT_CLASS (parent_class)->finalize (obj); } static gint html_a11y_hyper_link_get_start_index (AtkHyperlink *link) { HTMLA11YHyperLink *hl = HTML_A11Y_HYPER_LINK (link); HTMLText *text = HTML_TEXT (HTML_A11Y_HTML (hl->a11y.object)); Link *a = (Link *) g_slist_nth_data (text->links, hl->num); return a ? a->start_offset : -1; } static gint html_a11y_hyper_link_get_end_index (AtkHyperlink *link) { HTMLA11YHyperLink *hl = HTML_A11Y_HYPER_LINK (link); Link *a = (Link *) g_slist_nth_data (HTML_TEXT (HTML_A11Y_HTML (hl->a11y.object))->links, hl->num); return a ? a->end_offset : -1; } static void html_a11y_hyper_link_class_init (HTMLA11YHyperLinkClass *klass) { GObjectClass *gobject_class = G_OBJECT_CLASS (klass); AtkHyperlinkClass *atk_hyperlink_class = ATK_HYPERLINK_CLASS (klass); parent_class = g_type_class_peek_parent (klass); atk_hyperlink_class->get_start_index = html_a11y_hyper_link_get_start_index; atk_hyperlink_class->get_end_index = html_a11y_hyper_link_get_end_index; gobject_class->finalize = html_a11y_hyper_link_finalize; } static void html_a11y_hyper_link_init (HTMLA11YHyperLink *a11y_hyper_link) { a11y_hyper_link->description = NULL; } AtkHyperlink * html_a11y_hyper_link_new (HTMLA11Y *a11y, gint link_index) { HTMLA11YHyperLink *hl; g_return_val_if_fail (G_IS_HTML_A11Y (a11y), NULL); hl = HTML_A11Y_HYPER_LINK (g_object_new (G_TYPE_HTML_A11Y_HYPER_LINK, NULL)); hl->a11y.object = a11y; hl->num = link_index; hl->offset = ((Link *) g_slist_nth_data (HTML_TEXT (HTML_A11Y_HTML (a11y))->links, link_index))->start_offset; g_object_add_weak_pointer (G_OBJECT (hl->a11y.object), &hl->a11y.weakref); return ATK_HYPERLINK (hl); } /* * Action interface */ static gboolean html_a11y_hyper_link_do_action (AtkAction *action, gint i) { HTMLA11YHyperLink *hl; gboolean result = FALSE; hl = HTML_A11Y_HYPER_LINK (action); if (i == 0 && hl->a11y.object) { HTMLText *text = HTML_TEXT (HTML_A11Y_HTML (hl->a11y.object)); gchar *url = html_object_get_complete_url (HTML_OBJECT (text), hl->offset); if (url && *url) { GObject *gtkhtml = GTK_HTML_A11Y_GTKHTML_POINTER (html_a11y_get_gtkhtml_parent (HTML_A11Y (hl->a11y.object))); g_signal_emit_by_name (gtkhtml, "link_clicked", url); result = TRUE; } g_free (url); } return result; } static gint html_a11y_hyper_link_get_n_actions (AtkAction *action) { return 1; } static G_CONST_RETURN gchar * html_a11y_hyper_link_get_description (AtkAction *action, gint i) { if (i == 0) { HTMLA11YHyperLink *hl; hl = HTML_A11Y_HYPER_LINK (action); return hl->description; } return NULL; } static G_CONST_RETURN gchar * html_a11y_hyper_link_get_name (AtkAction *action, gint i) { return i == 0 ? "link click" : NULL; } static gboolean html_a11y_hyper_link_set_description (AtkAction *action, gint i, const gchar *description) { if (i == 0) { HTMLA11YHyperLink *hl; hl = HTML_A11Y_HYPER_LINK (action); g_free (hl->description); hl->description = g_strdup (description); return TRUE; } return FALSE; }