diff options
author | mattm@chromium.org <mattm@chromium.org@0039d316-1c4b-4281-b951-d872f2087c98> | 2011-08-13 03:49:13 +0000 |
---|---|---|
committer | mattm@chromium.org <mattm@chromium.org@0039d316-1c4b-4281-b951-d872f2087c98> | 2011-08-13 03:49:13 +0000 |
commit | 4845d5f6661bf58e556da21c36c1472125e81327 (patch) | |
tree | 9c0f3e674d66c4f1224447b64f8ea15f6a4376d2 /chrome/browser/ui/gtk/gtk_input_event_box.cc | |
parent | a3340f3d323f769460a1b269eb8198faf071e2a2 (diff) | |
download | chromium_src-4845d5f6661bf58e556da21c36c1472125e81327.zip chromium_src-4845d5f6661bf58e556da21c36c1472125e81327.tar.gz chromium_src-4845d5f6661bf58e556da21c36c1472125e81327.tar.bz2 |
Gtk: Make click target of tabs match their appearance.
BUG=87856
TEST=See bug
Review URL: http://codereview.chromium.org/7640004
git-svn-id: svn://svn.chromium.org/chrome/trunk/src@96674 0039d316-1c4b-4281-b951-d872f2087c98
Diffstat (limited to 'chrome/browser/ui/gtk/gtk_input_event_box.cc')
-rw-r--r-- | chrome/browser/ui/gtk/gtk_input_event_box.cc | 159 |
1 files changed, 159 insertions, 0 deletions
diff --git a/chrome/browser/ui/gtk/gtk_input_event_box.cc b/chrome/browser/ui/gtk/gtk_input_event_box.cc new file mode 100644 index 0000000..c554834 --- /dev/null +++ b/chrome/browser/ui/gtk/gtk_input_event_box.cc @@ -0,0 +1,159 @@ +// Copyright (c) 2011 The Chromium Authors. All rights reserved. +// Use of this source code is governed by a BSD-style license that can be +// found in the LICENSE file. + +#include "chrome/browser/ui/gtk/gtk_input_event_box.h" + +#include <gdk/gdkwindow.h> +#include <gtk/gtk.h> +#include <gtk/gtkwidget.h> +#include <gtk/gtkbin.h> + +G_BEGIN_DECLS + +#define GTK_INPUT_EVENT_BOX_GET_PRIVATE(o) (G_TYPE_INSTANCE_GET_PRIVATE ((o), \ + GTK_TYPE_INPUT_EVENT_BOX, \ + GtkInputEventBoxPrivate)) + +typedef struct _GtkInputEventBoxPrivate GtkInputEventBoxPrivate; + +struct _GtkInputEventBoxPrivate { + GdkWindow* event_window; +}; + +G_DEFINE_TYPE(GtkInputEventBox, gtk_input_event_box, GTK_TYPE_BIN) + +static void gtk_input_event_box_realize(GtkWidget* widget); +static void gtk_input_event_box_unrealize(GtkWidget* widget); +static void gtk_input_event_box_map(GtkWidget* widget); +static void gtk_input_event_box_unmap(GtkWidget* widget); +static void gtk_input_event_box_size_allocate(GtkWidget* widget, + GtkAllocation* allocation); +static void gtk_input_event_box_size_request(GtkWidget* widget, + GtkRequisition* requisition); + +static void gtk_input_event_box_class_init(GtkInputEventBoxClass* klass) { + GtkWidgetClass* widget_class = reinterpret_cast<GtkWidgetClass*>(klass); + widget_class->realize = gtk_input_event_box_realize; + widget_class->unrealize = gtk_input_event_box_unrealize; + widget_class->map = gtk_input_event_box_map; + widget_class->unmap = gtk_input_event_box_unmap; + widget_class->size_allocate = gtk_input_event_box_size_allocate; + widget_class->size_request = gtk_input_event_box_size_request; + + GObjectClass* gobject_class = G_OBJECT_CLASS(klass); + g_type_class_add_private(gobject_class, sizeof(GtkInputEventBoxPrivate)); +} + +static void gtk_input_event_box_init(GtkInputEventBox* widget) { + GtkInputEventBoxPrivate* priv = GTK_INPUT_EVENT_BOX_GET_PRIVATE(widget); + priv->event_window = NULL; +} + +GtkWidget* gtk_input_event_box_new() { + return GTK_WIDGET(g_object_new(GTK_TYPE_INPUT_EVENT_BOX, NULL)); +} + +static void gtk_input_event_box_realize(GtkWidget* widget) { + g_return_if_fail(GTK_IS_INPUT_EVENT_BOX(widget)); + + GtkInputEventBoxPrivate* priv = GTK_INPUT_EVENT_BOX_GET_PRIVATE(widget); + + GdkWindow* parent = gtk_widget_get_parent_window(widget); + GdkWindowAttr attributes; + GtkAllocation allocation; + gint attributes_mask = GDK_WA_X | GDK_WA_Y; + + gtk_widget_get_allocation(widget, &allocation); + + attributes.x = allocation.x; + attributes.y = allocation.y; + attributes.width = allocation.width; + attributes.height = allocation.height; + + attributes.window_type = GDK_WINDOW_CHILD; + attributes.wclass = GDK_INPUT_ONLY; + + attributes.event_mask = gtk_widget_get_events(widget) + | GDK_BUTTON_MOTION_MASK + | GDK_BUTTON_PRESS_MASK + | GDK_BUTTON_RELEASE_MASK + | GDK_EXPOSURE_MASK + | GDK_ENTER_NOTIFY_MASK + | GDK_LEAVE_NOTIFY_MASK; + + priv->event_window = gdk_window_new(parent, &attributes, attributes_mask); + gdk_window_set_user_data(priv->event_window, widget); + + GTK_WIDGET_CLASS(gtk_input_event_box_parent_class)->realize(widget); +} + +static void gtk_input_event_box_unrealize(GtkWidget* widget) { + g_return_if_fail(GTK_IS_INPUT_EVENT_BOX(widget)); + + GtkInputEventBoxPrivate* priv = GTK_INPUT_EVENT_BOX_GET_PRIVATE(widget); + if (priv->event_window) { + gdk_window_set_user_data(priv->event_window, NULL); + gdk_window_destroy(priv->event_window); + priv->event_window = NULL; + } + + GTK_WIDGET_CLASS(gtk_input_event_box_parent_class)->unrealize(widget); +} + +static void gtk_input_event_box_map(GtkWidget* widget) { + g_return_if_fail(GTK_IS_INPUT_EVENT_BOX(widget)); + + GtkInputEventBoxPrivate* priv = GTK_INPUT_EVENT_BOX_GET_PRIVATE(widget); + if (priv->event_window) + gdk_window_show(priv->event_window); + + GTK_WIDGET_CLASS(gtk_input_event_box_parent_class)->map(widget); +} + +static void gtk_input_event_box_unmap(GtkWidget* widget) { + g_return_if_fail(GTK_IS_INPUT_EVENT_BOX(widget)); + + GtkInputEventBoxPrivate* priv = GTK_INPUT_EVENT_BOX_GET_PRIVATE(widget); + if (priv->event_window) + gdk_window_hide(priv->event_window); + + GTK_WIDGET_CLASS(gtk_input_event_box_parent_class)->unmap(widget); +} + +static void gtk_input_event_box_size_allocate(GtkWidget* widget, + GtkAllocation* allocation) { + g_return_if_fail(GTK_IS_INPUT_EVENT_BOX(widget)); + + widget->allocation = *allocation; + + GtkInputEventBoxPrivate* priv = GTK_INPUT_EVENT_BOX_GET_PRIVATE(widget); + if (priv->event_window) { + gdk_window_move_resize(priv->event_window, + allocation->x, + allocation->y, + allocation->width, + allocation->height); + } + + GtkWidget* child = gtk_bin_get_child(GTK_BIN(widget)); + if (child) + gtk_widget_size_allocate(child, allocation); +} + +static void gtk_input_event_box_size_request(GtkWidget* widget, + GtkRequisition* requisition) { + + GtkWidget* child = gtk_bin_get_child(GTK_BIN(widget)); + if (child) + gtk_widget_size_request(child, requisition); +} + +GdkWindow* gtk_input_event_box_get_window(GtkInputEventBox* widget) { + g_return_val_if_fail(GTK_IS_INPUT_EVENT_BOX(widget), NULL); + + GtkInputEventBoxPrivate* priv = GTK_INPUT_EVENT_BOX_GET_PRIVATE(widget); + return priv->event_window; +} + +G_END_DECLS |