test plugin window existence at plugin instance destruction. b=485125,429604,454756 r=roc

This commit is contained in:
Karl Tomlinson 2009-05-18 13:53:39 +12:00
Родитель 2d23dfbf24
Коммит 3b94830dd0
3 изменённых файлов: 62 добавлений и 12 удалений

Просмотреть файл

@ -87,7 +87,7 @@ include $(topsrcdir)/config/rules.mk
ifeq ($(MOZ_WIDGET_TOOLKIT),gtk2)
CXXFLAGS += $(MOZ_GTK2_CFLAGS)
CFLAGS += $(MOZ_GTK2_CFLAGS)
EXTRA_DSO_LDOPTS += $(MOZ_GTK2_LIBS)
EXTRA_DSO_LDOPTS += $(MOZ_GTK2_LIBS) $(XLDFLAGS) $(XLIBS)
endif
install-plugin: $(SHARED_LIBRARY)

Просмотреть файл

@ -52,11 +52,13 @@ typedef struct TestNPObject : NPObject {
PRUint32 drawColor; // 0xAARRGGBB
} TestNPObject;
typedef struct _PlatformData PlatformData;
typedef struct InstanceData {
NPP npp;
NPWindow window;
TestNPObject* scriptableObject;
void* platformData;
PlatformData* platformData;
uint32_t instanceCountWatchGeneration;
bool lastReportedPrivateModeState;
bool hasWidget;

Просмотреть файл

@ -1,3 +1,4 @@
/* -*- Mode: C++; tab-width: 8; indent-tabs-mode: nil; c-basic-offset: 2 -*- */
/* ***** BEGIN LICENSE BLOCK *****
*
* Copyright (c) 2008, Mozilla Corporation
@ -48,6 +49,11 @@
* be fixed to use raw X APIs instead.
*/
struct _PlatformData {
Display* display;
GtkWidget* plug;
};
bool
pluginSupportsWindowMode()
{
@ -64,6 +70,14 @@ NPError
pluginInstanceInit(InstanceData* instanceData)
{
#ifdef MOZ_X11
instanceData->platformData = static_cast<PlatformData*>
(NPN_MemAlloc(sizeof(PlatformData)));
if (!instanceData->platformData)
return NPERR_OUT_OF_MEMORY_ERROR;
instanceData->platformData->display = 0;
instanceData->platformData->plug = 0;
return NPERR_NO_ERROR;
#else
// we only support X11 here, since thats what the plugin system uses
@ -74,13 +88,29 @@ pluginInstanceInit(InstanceData* instanceData)
void
pluginInstanceShutdown(InstanceData* instanceData)
{
GtkWidget* plug = static_cast<GtkWidget*>(instanceData->platformData);
if (plug) {
gtk_widget_destroy(plug);
instanceData->platformData = 0;
if (instanceData->hasWidget) {
Window window = reinterpret_cast<XID>(instanceData->window.window);
if (window != None) {
// This window XID should still be valid.
// See bug 429604 and bug 454756.
XWindowAttributes attributes;
if (!XGetWindowAttributes(instanceData->platformData->display, window,
&attributes))
g_error("XGetWindowAttributes failed at plugin instance shutdown");
}
}
GtkWidget* plug = instanceData->platformData->plug;
if (plug) {
instanceData->platformData->plug = 0;
gtk_widget_destroy(plug);
}
NPN_MemFree(instanceData->platformData);
instanceData->platformData = 0;
}
static void
SetCairoRGBA(cairo_t* cairoWindow, PRUint32 rgba)
{
@ -183,20 +213,36 @@ ExposeWidget(GtkWidget* widget, GdkEventExpose* event,
return TRUE;
}
static gboolean
DeleteWidget(GtkWidget* widget, GdkEvent* event, gpointer user_data)
{
InstanceData* instanceData = static_cast<InstanceData*>(user_data);
// Some plugins do not expect the plug to be removed from the socket before
// the plugin instance is destroyed. e.g. bug 485125
if (instanceData->platformData->plug)
g_error("plug removed"); // this aborts
return FALSE;
}
void
pluginDoSetWindow(InstanceData* instanceData, NPWindow* newWindow)
{
instanceData->window = *newWindow;
NPSetWindowCallbackStruct *ws_info =
static_cast<NPSetWindowCallbackStruct*>(newWindow->ws_info);
instanceData->platformData->display = ws_info->display;
}
void
pluginWidgetInit(InstanceData* instanceData, void* oldWindow)
{
#ifdef MOZ_X11
GtkWidget* oldPlug = static_cast<GtkWidget*>(instanceData->platformData);
GtkWidget* oldPlug = instanceData->platformData->plug;
if (oldPlug) {
instanceData->platformData->plug = 0;
gtk_widget_destroy(oldPlug);
instanceData->platformData = 0;
}
GdkNativeWindow nativeWinId =
@ -210,11 +256,13 @@ pluginWidgetInit(InstanceData* instanceData, void* oldWindow)
/* all the events that our widget wants to receive */
gtk_widget_add_events(plug, GDK_EXPOSURE_MASK);
g_signal_connect(G_OBJECT(plug), "event", G_CALLBACK(ExposeWidget),
g_signal_connect(G_OBJECT(plug), "expose-event", G_CALLBACK(ExposeWidget),
instanceData);
g_signal_connect(G_OBJECT(plug), "delete-event", G_CALLBACK(DeleteWidget),
instanceData);
gtk_widget_show(plug);
instanceData->platformData = plug;
instanceData->platformData->plug = plug;
#endif
}
@ -243,7 +291,7 @@ int32_t pluginGetEdge(InstanceData* instanceData, RectEdge edge)
{
if (!instanceData->hasWidget)
return NPTEST_INT32_ERROR;
GtkWidget* plug = static_cast<GtkWidget*>(instanceData->platformData);
GtkWidget* plug = instanceData->platformData->plug;
if (!plug)
return NPTEST_INT32_ERROR;
GdkWindow* plugWnd = plug->window;
@ -289,7 +337,7 @@ int32_t pluginGetClipRegionRectEdge(InstanceData* instanceData,
if (!instanceData->hasWidget)
return NPTEST_INT32_ERROR;
GtkWidget* plug = static_cast<GtkWidget*>(instanceData->platformData);
GtkWidget* plug = instanceData->platformData->plug;
if (!plug)
return NPTEST_INT32_ERROR;
GdkWindow* plugWnd = plug->window;