summaryrefslogtreecommitdiffstats
path: root/webkit/glue/plugins/webplugin_delegate_impl_gtk.cc
diff options
context:
space:
mode:
Diffstat (limited to 'webkit/glue/plugins/webplugin_delegate_impl_gtk.cc')
-rw-r--r--webkit/glue/plugins/webplugin_delegate_impl_gtk.cc61
1 files changed, 57 insertions, 4 deletions
diff --git a/webkit/glue/plugins/webplugin_delegate_impl_gtk.cc b/webkit/glue/plugins/webplugin_delegate_impl_gtk.cc
index 741ba99..58207c6 100644
--- a/webkit/glue/plugins/webplugin_delegate_impl_gtk.cc
+++ b/webkit/glue/plugins/webplugin_delegate_impl_gtk.cc
@@ -21,6 +21,7 @@
#include <gtk/gtk.h>
#include <gdk/gdkx.h>
+#include "base/basictypes.h"
#include "base/file_util.h"
#include "base/message_loop.h"
#include "base/process_util.h"
@@ -241,13 +242,60 @@ void WebPluginDelegateImpl::WindowedUpdateGeometry(
namespace {
+// This is just a GtkSocket, with size_request overridden, so that we always
+// control the size of the widget.
+class GtkFixedSocket {
+ public:
+ // Create a new instance of our GTK widget object.
+ static GtkWidget* CreateNewWidget() {
+ return GTK_WIDGET(g_object_new(GetType(), NULL));
+ }
+
+ private:
+ // Create and register our custom container type with GTK.
+ static GType GetType() {
+ static GType type = 0; // We only want to register our type once.
+ if (!type) {
+ static const GTypeInfo info = {
+ sizeof(GtkSocketClass),
+ NULL, NULL,
+ static_cast<GClassInitFunc>(&ClassInit),
+ NULL, NULL,
+ sizeof(GtkSocket), // We are identical to a GtkSocket.
+ 0, NULL,
+ };
+ type = g_type_register_static(GTK_TYPE_SOCKET,
+ "GtkFixedSocket",
+ &info,
+ static_cast<GTypeFlags>(0));
+ }
+ return type;
+ }
+
+ // Implementation of the class initializer.
+ static void ClassInit(gpointer klass, gpointer class_data_unusued) {
+ GtkWidgetClass* widget_class = reinterpret_cast<GtkWidgetClass*>(klass);
+ widget_class->size_request = &HandleSizeRequest;
+ }
+
+ // Report our allocation size during size requisition. This means we control
+ // the size, from calling gtk_widget_size_allocate in WindowedReposition().
+ static void HandleSizeRequest(GtkWidget* widget,
+ GtkRequisition* requisition) {
+ requisition->width = widget->allocation.width;
+ requisition->height = widget->allocation.height;
+ }
+
+ DISALLOW_IMPLICIT_CONSTRUCTORS(GtkFixedSocket);
+};
+
gboolean PlugRemovedCallback(GtkSocket* socket) {
// This is called when the other side of the socket goes away.
// We return TRUE to indicate that we don't want to destroy our side.
return TRUE;
}
-}
+} // namespace
bool WebPluginDelegateImpl::WindowedCreatePlugin() {
DCHECK(!windowed_handle_);
@@ -260,16 +308,18 @@ bool WebPluginDelegateImpl::WindowedCreatePlugin() {
return false;
}
- windowed_handle_ = gtk_socket_new();
- gtk_widget_set_parent(windowed_handle_, parent_);
+ windowed_handle_ = GtkFixedSocket::CreateNewWidget();
g_signal_connect(GTK_SOCKET(windowed_handle_), "plug-removed",
G_CALLBACK(PlugRemovedCallback), NULL);
+ gtk_container_add(GTK_CONTAINER(parent_), windowed_handle_);
// TODO(evanm): connect to signals on the socket, like when the other side
// goes away.
+ gtk_widget_show(windowed_handle_);
+ gtk_widget_realize(windowed_handle_);
+
window_.window = GINT_TO_POINTER(
gtk_socket_get_id(GTK_SOCKET(windowed_handle_)));
- gtk_widget_show(windowed_handle_);
NPSetWindowCallbackStruct* extra = new NPSetWindowCallbackStruct;
extra->display = GDK_WINDOW_XDISPLAY(windowed_handle_->window);
@@ -303,6 +353,9 @@ bool WebPluginDelegateImpl::WindowedReposition(
// Clipping is handled by WebPlugin.
GtkAllocation allocation = { window_rect.x(), window_rect.y(),
window_rect.width(), window_rect.height() };
+ // Tell our parent GtkFixed container where to place the widget.
+ gtk_fixed_move(
+ GTK_FIXED(parent_), windowed_handle_, window_rect.x(), window_rect.y());
gtk_widget_size_allocate(windowed_handle_, &allocation);
window_rect_ = window_rect;