Closed Bug 464966 Opened 16 years ago Closed 14 years ago

Add NPAPI Plugin support for Mozilla Qt

Categories

(Core Graveyard :: Plug-ins, defect)

x86
Linux
defect
Not set
normal

Tracking

(Not tracked)

RESOLVED FIXED

People

(Reporter: siraj.razick, Assigned: romaxa)

References

Details

Attachments

(2 files, 14 obsolete files)

26.31 KB, patch
karlt
: review+
Details | Diff | Splinter Review
7.83 KB, patch
karlt
: review+
Details | Diff | Splinter Review
User-Agent:       Mozilla/5.0 (X11; U; Linux i686; en-US; rv:1.9.1b2pre) Gecko/20081115 Minefield/3.1b2pre
Build Identifier: Mozilla/5.0 (X11; U; Linux i686; en-US; rv:1.9.1b2pre) Gecko/20081115 Minefield/3.1b2pre

Add NPAPI plugin support for Mozilla Qt port. 

Reproducible: Always

Steps to Reproduce:
1. Ex: goto a site like youtube.com using Mozilla Qt 
2. NPAPI Plugins are not working 
3.
Actual Results:  
NPAPI plugins are not loading on the Mozilla Qt

Expected Results:  
NPAPI plugins should load when using Mozilla Qt 

I'll attach a patch for this shortly
This patch basically adds loading and displaying NPAPI plugins such as Flash. It  would be great to get an initial review so I can follow up on this next week, if there are adjustments to be made :). 

Thank you :)
Attachment #348274 - Flags: review?(pavlov)
Status: UNCONFIRMED → NEW
Ever confirmed: true
Attached patch Version 2 with some code cleanup (obsolete) — Splinter Review
Functionality is similar to the previous patch, this patch cleans up some of the previous code.

btw I'm working on the windowless mode till this patch gets reviewed :), but standing by to make any required alterations to get this patch landed.  

Thank you :)
Attachment #348274 - Attachment is obsolete: true
Attachment #352126 - Flags: superreview?(pavlov)
Attachment #352126 - Flags: review?(pavlov)
Attachment #348274 - Flags: review?(pavlov)
Attachment #352126 - Flags: superreview?(vladimir)
Attachment #352126 - Flags: superreview?(pavlov)
Attachment #352126 - Flags: review?(pavlov)
Attachment #352126 - Flags: review?(jst)
Comment on attachment 352126 [details] [diff] [review]
Version 2 with some code cleanup

- In nsPluginNativeWindowQt::CallSetWindow():

+  if (aPluginInstance) {
+    if (type == nsPluginWindowType_Window) {
[...]
+      if (needXEmbed) {
[...]
+        if (!mContainer) {
+          mContainer = new  QX11EmbedContainer(parent);
+          mContainer->resize(width,height);
+          mContainer->show();
+          mWsInfo.display = mContainer->x11Info().display();
+          mWsInfo.colormap = mContainer->x11Info().colormap();
+          mWsInfo.visual = (Visual*)mContainer->x11Info().visual();
+          mWsInfo.depth = mContainer->x11Info().depth();
+          window = (nsPluginPort*) mContainer->winId();
+          aPluginInstance->SetWindow(this);
+        }
+      }
+    }

Don't we want to call SetWindow() in the non-XEmbed case here too? Or is that something that's just not supported at all in Qt?

r=jst assuming the above is either what we want or fixed.
Attachment #352126 - Flags: review?(jst) → review+
(In reply to comment #3)
> (From update of attachment 352126 [details] [diff] [review])
> - In nsPluginNativeWindowQt::CallSetWindow():
> 
> +  if (aPluginInstance) {
> +    if (type == nsPluginWindowType_Window) {
> [...]
> +      if (needXEmbed) {
> [...]
> +        if (!mContainer) {
> +          mContainer = new  QX11EmbedContainer(parent);
> +          mContainer->resize(width,height);
> +          mContainer->show();
> +          mWsInfo.display = mContainer->x11Info().display();
> +          mWsInfo.colormap = mContainer->x11Info().colormap();
> +          mWsInfo.visual = (Visual*)mContainer->x11Info().visual();
> +          mWsInfo.depth = mContainer->x11Info().depth();
> +          window = (nsPluginPort*) mContainer->winId();
> +          aPluginInstance->SetWindow(this);
> +        }
> +      }
> +    }
> 
> Don't we want to call SetWindow() in the non-XEmbed case here too? Or is that
> something that's just not supported at all in Qt?
> 
Hi, 

Thank you for taking time to review the patch ! :). 



Old-style Xt plugins are handled in Gtk-port using Gtk2XtBin Widget Implementation library, since MozillaQt doesn't have a similar support library yet, I avoided calling SetWindow() for the non-XEmbed case.

> r=jst assuming the above is either what we want or fixed.
This is a work in progress patch, which makes windowless plugins work. 
known issue : the x an y offset seems to be wrong. 
things that work
* Detection of windowless mode
* mouse events 
* rendering and expose event
Assignee: nobody → siraj.razick
Component: General → Plug-ins
Product: Firefox → Core
QA Contact: general → plugins
(In reply to comment #5)
> Created an attachment (id=355155) [details]
> Work in Progress patch for Windowless mode under Qt
> 
> This is a work in progress patch, which makes windowless plugins work. 
> known issue : the x an y offset seems to be wrong. 
> things that work
> * Detection of windowless mode
> * mouse events 
> * rendering and expose event

thank you very very much. The patch is very important for us. Let me try.
It's delicious successful patch.  Thank you !!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!
(In reply to comment #7)
> It's delicious successful patch.  Thank you !!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!

Which version of MozillaQt did you try this patch on?  The patch failed with the latest Mozilla code.  It complains about missing nsPluginHostImpl.cpp.  Has this file been renamed or moved in the latest Mozilla code?
nsPluginHostImpl.cpp was renamed, dropped the "impl".
Comment on attachment 352126 [details] [diff] [review]
Version 2 with some code cleanup

this is probably fine, sorry it took a while -- would like dougt to confirm though as he's been doing some Qt work stuff
Attachment #352126 - Flags: superreview?(vladimir)
Attachment #352126 - Flags: superreview+
Attachment #352126 - Flags: review?(dougt)
I think we need to merge this and changes from bug https://bugzilla.mozilla.org/show_bug.cgi?id=527416
and make sure that we have working plugins on Qt port
(In reply to comment #8)
> (In reply to comment #7)
> > It's delicious successful patch.  Thank you !!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!
> 
> Which version of MozillaQt did you try this patch on?  The patch failed with
> the latest Mozilla code.  It complains about missing nsPluginHostImpl.cpp.  Has
> this file been renamed or moved in the latest Mozilla code?

try 	FIREFOX_3_5_7_RELEASE.
what oleg said.  I do not think we should worry about Qt running on any older branch at this point.
Assignee: siraj.razick → romaxa
Attachment #352126 - Attachment is obsolete: true
Attachment #355155 - Attachment is obsolete: true
Status: NEW → ASSIGNED
Attachment #352126 - Flags: review?(dougt)
Attached patch Updated patch (obsolete) — Splinter Review
Updated style, added test plugin changes, Improved Windowless rendering on gfxImageSurface
Attachment #434675 - Attachment is obsolete: true
Attachment #435646 - Flags: review?(dougt)
(In reply to comment #11)
> I think we need to merge this and changes from bug
> https://bugzilla.mozilla.org/show_bug.cgi?id=527416
> and make sure that we have working plugins on Qt port

Fully agree. Let's get that done and mark 527416 as duplicate of this bug.
Is this the first Qt NPAPI implementation? Do other browsers have this already and if so, what is your reference for the API?

I want to make sure that if we're adding/changing a spec, that we write out the new spec (https://wiki.mozilla.org/Plugins).
(In reply to comment #18)
> Is this the first Qt NPAPI implementation? 

It is not Qt NPAPI... it is normal XWindowLess compatible API implementation for Qt port.
OK - so long as the interaction between the Qt port and plugins is exactly the same as for Gtk/X11 then never mind about the spec. But if there are any functional differences, they need to be documented.
I think we are not going to support windowed plugins..
Attachment #435646 - Flags: review?(dougt)
Comment on attachment 435646 [details] [diff] [review]
Updated patch

I think I need to rework a bit gfxQtNativeRenderer.cpp

implementation, and make sure that it is painting correctly opaque/transparent plugins on SurfaceTypeQPainter and SurfaceTypeImage
oleg, maybe we should push for doing OOPP since you are in the middle of thinking about plugins.  Make draw into a layer, and have that composited using layers.
I'm thinking about transparent mode problem...
way of painting in attached patch does not provide any transparency support at all.

Current (gtk) path of transparent plugins rendering work in this way:
Create temp surface -> paint layout part to temp surface -> give surface to plugin -> plugin will do blending by themselves (flash) -> composite temp surface back to layout context.

With layers I assume it will work in this way:
Plugin render transparent data to layer surface, and layer compositor does blending on engine side.

I'm not sure is it good to move blending on engine side or not?
Is it documented anywhere about where blending should happen? on engine or plugins side... 
and can we provide ARGB surface to plugin and expect that plugin will paint transparent data?
Attached patch Updated and working patch (obsolete) — Splinter Review
Added 32bpp XSurface creation for transparent plugins rendering.
Added some MOZ_X11 ifdefs.
I think this is enough for default Xwindowless support
Attachment #435646 - Attachment is obsolete: true
Attachment #436194 - Flags: review?(dougt)
Attachment #436194 - Flags: review?(dougt) → review?(karlt)
marking dumb comment above private.
Attached patch Updated version. (obsolete) — Splinter Review
A bit better handling for 32 X surfaces.
Fixed sending of proper visual, colormap to plugin (pixmap.x11Info() returning default values).
Attachment #437572 - Flags: review?(karlt)
Comment on attachment 436194 [details] [diff] [review]
Updated and working patch

Marking this one as obsolete
Attachment #436194 - Flags: review?(karlt)
Attached patch Ups minor merge problem (obsolete) — Splinter Review
Attachment #436194 - Attachment is obsolete: true
Attachment #437572 - Attachment is obsolete: true
Attachment #437596 - Flags: review?(karlt)
Attachment #437572 - Flags: review?(karlt)
With this fix we can get XSurface data with one memcpy cost
Attachment #437919 - Flags: review?(karlt)
Comment on attachment 437596 [details] [diff] [review]
Ups minor merge problem

> #ifdef MOZ_X11
>   *static_cast<Window*>(value) = widget->handle();
>+#else
>+  *static_cast<QWidget*>(value) = widget;

Is there any point in doing anything (beyond returning failure) for non-X11
platforms at this stage?

> #ifdef MOZ_WIDGET_GTK2
>         Window root = GDK_ROOT_WINDOW();
>+#elif defined(MOZ_WIDGET_QT) && defined(MOZ_X11)
>+        Window root = QX11Info::appRootWindow();
> #else

The surrounding preprocessor conditional is already ifdef MOZ_X11.

>-#ifdef MOZ_WIDGET_GTK2
>+#ifdef MOZ_X11
>           else {
>-            ws_info->display = GDK_DISPLAY();
>+            ws_info->display = DISPLAY();
>           }
> #endif
> #endif

Here too.

>-  NPSetWindowCallbackStruct* ws_info = 
>+  NPSetWindowCallbackStruct* ws_info =

Unnecessary whitespace change.

>  * ***** END LICENSE BLOCK ***** */
> 
>+#ifdef MOZ_WIDGET_QT
>+#include <QX11Info>
>+#endif
>+
> #ifdef MOZ_IPC

It would be nice to move this to next to the other platform-specific includes,
if practical.

>+  /**
>+    Returns PR_TRUE
>+   */
>+  PRBool    CanGetValueFromPlugin(nsCOMPtr<nsIPluginInstance> &aPluginInstance);

:D Nice comment, but let's not bother with this function.

> CPPSRCS += nptest_qt.cpp
>+include $(topsrcdir)/config/config.mk
>+CXXFLAGS        += $(MOZ_QT_CFLAGS) $(GLIB_CFLAGS)
>+CFLAGS          += $(MOZ_QT_CFLAGS) $(GLIB_CFLAGS)
>+EXTRA_DSO_LDOPTS = \
>+                $(MOZ_QT_LIBS) \
>+                $(GLIB_LIBS) \
>+                $(XLDFLAGS) \
>+                $(XLIBS) \
>+                $(XEXT_LIB)

GLIB_CFLAGS GLIB_LIBS and XEXT_LIBS are unused.

>+static void pluginDrawWindow(InstanceData* instanceData, void* event);

Move this forward declaration to nptest_qt.cpp.

>+#ifdef MOZ_X11
>+#include <X11/extensions/shape.h>
>+#endif

Unused.

> int16_t
> pluginHandleEvent(InstanceData* instanceData, void* event)
> {
>-  return 0;

>+  case Expose: {
>+    //printf("Expose\n");
>+    break;
>+  }
>+  case NoExpose: {
>+    //printf("NoExpose\n");
>+    break;
>+  }
>+  case MapRequest: {
>+    //printf("MapRequest\n");
>+    break;
>+  }
>+  case ResizeRequest: {
>+    //printf("ResizeRequest\n");
>+    break;
>+  }
>+  case ConfigureRequest: {
>+    //printf("ConfigureRequest\n");
>+    break;
>+  }
>+  case CirculateRequest: {
>+    //printf("Circulate\n");
>+    break;
>+  }
>+  case SelectionClear: {
>+    //printf("SelectionClear\n");
>+    break;
>+  }

This function receives events from the browser rather than Xlib and so only
receives a subset of X event types.  The above events are never sent to the
plugin.

>+  return NPERR_NO_ERROR;
> }

Better to write "0" for the return value as it is not an error code but
indicates whether or not the event was handled.

>+  QPixmap pixmap = QPixmap::fromX11Pixmap((XID)(((XGraphicsExposeEvent*)event)->drawable),QPixmap::ExplicitlyShared);

The (XID)() cast should not be necessary.

How does the QPixmap know/choose which Visual/Colormap to use when drawing?

>+    painter.fillRect(QRect(x,y,width,height), drawColor);

This should restrict drawing to window.clipRect or to the rect in the
XGraphicsExposeEvent.  (The gtk plugin actually does both, to test both
rects.)

> ifeq (qt,$(MOZ_WIDGET_TOOLKIT))
>-EXTRA_DSO_LDOPTS += $(XLDFLAGS) $(XLIBS) $(XT_LIBS) $(MOZ_QT_LIBS) -lgthread-2.0
>+EXTRA_DSO_LDOPTS += $(XLDFLAGS) $(XLIBS) $(XT_LIBS) $(MOZ_QT_LIBS) -lgthread-2.0 $(XEXT_LIBS) $(XCOMPOSITE_LIBS)

XCOMPOSITE_LIBS is unused.
XEXT_LIBS is not used in this patch, but attachment 437919 [details] [diff] [review] would need it.

What's the plan for windowed plugins?
I'd rather not have the code for windowed plugins (including
MOZ_COMPOSITED_PLUGINS) if they are not going to be supported.

I'm still looking at the NativeRenderer changes.
> >+#else
> >+  *static_cast<QWidget*>(value) = widget;
> 
> Is there any point in doing anything (beyond returning failure) for non-X11
> platforms at this stage?

yep, probably in OOP case it does not make sense to return widget pointer...

> It would be nice to move this to next to the other platform-specific includes,
> if practical.

That is fail to compile... see:
https://bugzilla.mozilla.org/show_bug.cgi?id=441324


> What's the plan for windowed plugins?

currently no support

> I'd rather not have the code for windowed plugins (including
> MOZ_COMPOSITED_PLUGINS) if they are not going to be supported.

Ok, I'll remove that
Attached patch Updated with existing comments (obsolete) — Splinter Review
Attachment #437596 - Flags: review?(karlt) → review-
Comment on attachment 437596 [details] [diff] [review]
Ups minor merge problem

There are a number of different issues to consider and special cases to optimize in the Native Renderer.

Some history about the Xlib NativeRenderers:
The code that does all this is in cairo-xlib-utils.c.
It used to be mostly toolkit independent until this apparently unreviewed
change added GDK dependencies.
http://hg.mozilla.org/mozilla-central/rev/5c77a12fedd5
I tried to back out much of that in bug 449959 comment 21 but didn't know
enough about QPainter and its cairo surface backend to sort things out
properly.

The key decision here is whether develop another Xlib NativeRenderer
customized for Qt or whether to use cairo-xlib-utils.c (perhaps almost
restoring to the pre-5c77a12fedd5 version) and optimize from there.  This Qt
version is really in its infancy and so now is a good time to pick a path.

Really the optimizations that will work for Qt (on X11) will also be
appropriate for other toolkits on X11, and I think ideally the best solution
for all will be that they all use and optimize cairo-xlib-utils.c (even if it
some toolkit-specific sections will be necessary).  I guess eventually there
would be code to extract Xlib surfaces from cairo_qpainter_surfaces and that
would require C++ (though even this Qt-specific version does not yet have that
optimization).

The main problem with the Qt version as-is is that it is using Qt rather than
the gfxContent to blend to the underlying target surface in the context.  The
gfxContext can contain clip regions, which are not being considered.  The best
solution seems to be using the gfxContext or its underlying cairo_t to do
this.  (Even if there is a way to convert the cairo_t to a Qt equivalent,
using the existing cairo_t seems simpler.)

There are optimizations that can be done to draw directly to the underlying
surface when it is a Pixmap.  cairo-xlib-utils.c has some of the logic for
that though it will need to be extended for qtpainter surfaces with the X11
native engine.

Optimizations could also be done to use XShm in some situations.  These are
not yet done in cairo-xlib-utils.c, but they should be just as useful for
other toolkit ports as with Qt.  (And if it's useful here then it's probably
also useful in cairo.) 

Some other nits below but whether they are important depends on whether this
just uses cairo-xlib-utils.

(If you like, we can review the non-NativeRenderer changes separately and get
them landed.)

>+Visual *GetVisualByDepth(Display *aDisplay, int aDepth)

static

> {
>+    Visual *visual = NULL;
>+    Screen *screen = DefaultScreenOfDisplay(aDisplay);
>+    int j;
>+    for (j = 0; j < screen->ndepths; j++) {
>+        Depth *d = &screen->depths[j];
>+        if (d->depth == 32 && d->nvisuals && &d->visuals[0]) {

Either s/32/aDepth/ or s/GetVisualByDepth/GetARGBVisual/ or similar.

>+            visual = &d->visuals[0];
>+            break;

Check that visual->class is TrueColor before |break|ing.
(DirectColor visuals need a colormap to be allocated.)

>+    int depth = (flags & DRAW_IS_OPAQUE) ? QX11Info().depth() : 32;
>+    Visual *visual = GetVisualByDepth(QX11Info().display(), depth);

When DRAW_IS_OPAQUE, the visual can be obtained from QX11Info.

The 32-bit pixmap will cause a BadMatch fatal error with x86/amd64 Flash
(See bug 445250 comment 4), but I guess you know that.

>+    NS_ENSURE_TRUE(visual, NS_ERROR_FAILURE);

Avoid hiding early returns with NS_ENSURE_*.
Use

  if (!visual)
      return NS_ERROR_FAILURE.

>+    NS_ENSURE_TRUE(xsurf, NS_ERROR_FAILURE);

There shouldn't be any need to check for NULL return from |new|.

>+    QPixmap map = QPixmap::fromX11Pixmap(xsurf->XDrawable(), QPixmap::ExplicitlyShared);
>+    if(!(flags & DRAW_IS_OPAQUE))
>+        map.fill(QColor(255, 255, 255, 0));

QPixmap is not told the depth (even though we already know it) and so I'm
guessing it would need to query the X server, which may be another reason to
use cairo rather than QPainter.

>+    if (ctx->OriginalSurface()->GetType() == gfxASurface::SurfaceTypeQPainter) {

We should at least have a comment mentioning that this might already have an
underlying X Pixmap, in which case this could sometimes be optimized to skip
the temporary and blend.

In nsPluginInstanceOwner::Renderer::NativeDraw

>+  Colormap colormap = XCreateColormap(display, RootWindowOfScreen(screen),
>+                                      visual, AllocNone);

Creating a colormap every time is probably not desirable.
The colormap from QX11Info can be used when the visual came from there
(and the colormap created only when the visual differs).

The colormap's entries are initially undefined for non-static
(e.g. PseudoColor, DirectColor) visual classes, but if the visuals are only
TrueColor visuals this should be fine.

There is also an early return where the colormap is not freed.

It's probably simplest to choose or create a colormap in the NativeRenderer and pass it to NativeDraw.
I think we should do it in two steps. first is common changes without NativeRenderer and then fix rendering correctly
Attachment #437596 - Attachment is obsolete: true
Attachment #438698 - Attachment is obsolete: true
Attachment #439101 - Flags: review?(karlt)
Comment on attachment 439101 [details] [diff] [review]
Fixed comments, removed NativeRenderer changes, and make it empty for next part

>diff -r a388481c3f5e gfx/thebes/public/gfxQtNativeRenderer.h
>--- a/gfx/thebes/public/gfxQtNativeRenderer.h	Mon Apr 12 12:34:02 2010 +1200
>+++ b/gfx/thebes/public/gfxQtNativeRenderer.h	Thu Apr 15 00:54:52 2010 +0300
>@@ -38,13 +38,13 @@
> #ifndef GFXQTNATIVERENDER_H_
> #define GFXQTNATIVERENDER_H_
> 
> #include "gfxColor.h"
> #include "gfxASurface.h"
>+#include "gfxXlibSurface.h"
> #include "gfxContext.h"
> 
>-class QWidget;
> class QRect;
> 
> /**
>  * This class lets us take code that draws into an Qt drawable and lets us
>  * use it to draw into any Thebes context. The user should subclass this class,
>@@ -59,13 +59,15 @@ public:
>      * @param offsetY draw at this offset into the given drawable
>      * @param clipRects an array of rects; clip to the union
>      * @param numClipRects the number of rects in the array, or zero if
>      * no clipping is required
>      */
>-    virtual nsresult NativeDraw(QWidget * drawable, short offsetX, 
>-            short offsetY, QRect * clipRects, PRUint32 numClipRects) = 0;
>-  
>+    virtual nsresult NativeDraw(gfxXlibSurface *xsurf,
>+                                Colormap colormap,
>+                                short offsetX, short offsetY,
>+                                QRect * clipRects, PRUint32 numClipRects) = 0;
>+
>     enum {
>         // If set, then Draw() is opaque, i.e., every pixel in the intersection
>         // of the clipRect and (offset.x,offset.y,bounds.width,bounds.height)
>         // will be set and there is no dependence on what the existing pixels
>         // in the drawable are set to.

Don't change these yet, please.  Save these changes for the NativeRenderer
patch (when it'll be clearer what the API should be).

>-#ifdef MOZ_X11
> #ifdef MOZ_WIDGET_QT
> #include <QWidget>
>+#include <QPainter>
>+#ifdef MOZ_X11

I don't think QPainter is used.

>-    virtual nsresult NativeDraw(QWidget * drawable, short offsetX, 
>-            short offsetY, QRect * clipRects, PRUint32 numClipRects);
>+    virtual nsresult NativeDraw(gfxXlibSurface *xsurface,
>+                                Colormap colormap,
>+                                short offsetX, short offsetY,
>+                                QRect * clipRects, PRUint32 numClipRects);

>@@ -5381,20 +5397,20 @@ nsPluginInstanceOwner::Renderer::NativeD
>   Colormap colormap = GDK_COLORMAP_XCOLORMAP(gdk_drawable_get_colormap(drawable));
>   Screen * screen = GDK_SCREEN_XSCREEN (gdk_drawable_get_screen(drawable));
> #endif
> #elif defined(MOZ_WIDGET_QT)
> nsresult
>-nsPluginInstanceOwner::Renderer::NativeDraw(QWidget * drawable,
>+nsPluginInstanceOwner::Renderer::NativeDraw(gfxXlibSurface *xsurface,
>+                                            Colormap colormap,
>                                             short offsetX, short offsetY,
>                                             QRect * clipRects,
>                                             PRUint32 numClipRects)
> {
> #ifdef MOZ_X11
>-  QX11Info xinfo = drawable->x11Info();
>-  Visual * visual = (Visual*) xinfo.visual();
>-  Colormap colormap = xinfo.colormap();
>-  Screen * screen = (Screen*) xinfo.screen();
>+  Display *display = xsurface->XDisplay();
>+  Visual * visual = cairo_xlib_surface_get_visual(xsurface->CairoSurface());
>+  Screen *screen = cairo_xlib_surface_get_screen(xsurface->CairoSurface());
> #endif
> #endif
>   // See if the plugin must be notified of new window parameters.
>   PRBool doupdatewindow = PR_FALSE;
> 
>@@ -5488,15 +5504,14 @@ nsPluginInstanceOwner::Renderer::NativeD
>     XEvent pluginEvent;
>     XGraphicsExposeEvent& exposeEvent = pluginEvent.xgraphicsexpose;
>     // set the drawing info
>     exposeEvent.type = GraphicsExpose;
>     exposeEvent.display = DisplayOfScreen(screen);
>-    exposeEvent.drawable =
> #if defined(MOZ_WIDGET_GTK2)
>-      GDK_DRAWABLE_XID(drawable);
>+    exposeEvent.drawable = GDK_DRAWABLE_XID(drawable);
> #elif defined(MOZ_WIDGET_QT)
>-      drawable->x11PictureHandle();
>+    exposeEvent.drawable = xsurface->XDrawable();
> #endif

Save these changes for the NativeRenderer patch.

>+  // Creates XEmbed window
>+  nsresult  CreateXEmbedWindow();
>+
>+  // Resizes widget
>+  void      SetAllocation();
>+
>+  // Returns PR_TRUE if plugin allow to use NPP_GetValue
>+  PRBool    CanGetValueFromPlugin(nsCOMPtr<nsIPluginInstance> &aPluginInstance);
>+
>+  // Container widget which is used to contain plugin window
>+  QX11EmbedContainer* mContainerWidget;

No need for these with no windowed plugins.
nsPluginNativeWindowQt::CallSetWindow can just return early with an error when
type == NPWindowTypeWindow.

> CPPSRCS += nptest_qt.cpp
>+include $(topsrcdir)/config/config.mk
>+CXXFLAGS        += $(MOZ_QT_CFLAGS)
>+CFLAGS          += $(MOZ_QT_CFLAGS)
>+EXTRA_DSO_LDOPTS = \
>+                $(MOZ_QT_LIBS) \
>+                $(GLIB_LIBS) \

GLIB_LIBS is not used.

>+  QColor color;
>+  QPainter painter(&pixmap);
>+  QRect theRect(x, y, width, height);
>+  painter.fillRect(theRect, QColor(128,128,128,255));
>+  painter.drawRect(theRect);
>+  painter.drawText(QRect(theRect), Qt::AlignCenter, text);

Set the clip on the QPainter to window.clipRect (or the expose rect is OK).

>+  case Expose: {
>+    //printf("Expose\n");
>+    break;
>+  }
>+  case NoExpose: {
>+    //printf("NoExpose\n");
>+    break;
>+  }
>+  case MapRequest: {
>+    //printf("MapRequest\n");
>+    break;
>+  }
>+  case ResizeRequest: {
>+    //printf("ResizeRequest\n");
>+    break;
>+  }
>+  case ConfigureRequest: {
>+    //printf("ConfigureRequest\n");
>+    break;
>+  }
>+  case CirculateRequest: {
>+    //printf("Circulate\n");
>+    break;
>+  }
>+  case SelectionClear: {
>+    //printf("SelectionClear\n");
>+    break;
>+  }

Remove these please.

>-EXTRA_DSO_LDOPTS += $(XLDFLAGS) $(XLIBS) $(XT_LIBS) $(MOZ_QT_LIBS) -lgthread-2.0
>+EXTRA_DSO_LDOPTS += $(XLDFLAGS) $(XLIBS) $(XT_LIBS) $(MOZ_QT_LIBS) -lgthread-2.0 $(XEXT_LIBS)

Not needed.
Attachment #439101 - Flags: review?(karlt) → review-
Attached patch Updated with comments (obsolete) — Splinter Review
Attachment #439101 - Attachment is obsolete: true
Attachment #439269 - Flags: review?(karlt)
Comment on attachment 439269 [details] [diff] [review]
Updated with comments

This patch lost the function names and context (-pU8).

> #ifdef MOZ_X11
> #include <X11/Xlib.h>
>+#include <cairo-xlib.h>

Remove this,

> #elif defined(MOZ_WIDGET_QT)
>-      drawable->x11PictureHandle();
>+      drawable->handle();

this,

>   case NPNVSupportsXEmbedBool: {
>-#ifdef MOZ_WIDGET_GTK2
>+#if defined (MOZ_WIDGET_GTK2) || defined(MOZ_WIDGET_QT)

this,

>+#include <QDebug>
>+#include <QWidget>
>+#include <QX11EmbedContainer>
>+#include <QX11EmbedWidget>
>+#include <QHash>
>+#include <QX11Info>
>+#include <QApplication>

and these.

>+#include <QDebug>
> #include "nptest_platform.h"

It doesn't look like QDebug is used.
Attachment #439269 - Flags: review?(karlt) → review-
> > #elif defined(MOZ_WIDGET_QT)
> >-      drawable->x11PictureHandle();
> >+      drawable->handle();
> 
> this,
this is logically needed here, because  x11PictureHandle - it is XRender picture, and handle is Drawable, and we should give Drawable to plugin.
(In reply to comment #42)
> > >-      drawable->x11PictureHandle();
> > >+      drawable->handle();

> this is logically needed here, because  x11PictureHandle - it is XRender
> picture, and handle is Drawable, and we should give Drawable to plugin.

OK.  That sounds good then, thanks.  The picture is not right.
I couldn't see QWidget::handle() here:
http://qt.nokia.com/doc/4.7-snapshot/qwidget.html
> OK.  That sounds good then, thanks.  The picture is not right.
> I couldn't see QWidget::handle() here:
> http://qt.nokia.com/doc/4.7-snapshot/qwidget.html

It is X specific API. and not available on for example windows...
see 
http://qt.gitorious.org/qt/qt/blobs/4.7/src/gui/kernel/qwidget.h#line588
Attachment #439269 - Attachment is obsolete: true
Attachment #439889 - Flags: review?(karlt)
Attachment #439944 - Flags: review?(karlt)
Attachment #439944 - Flags: review?(karlt) → review+
Comment on attachment 439944 [details] [diff] [review]
More simple NativeRenderer version

This looks much better, thanks.

>diff -r 7af9266d6c21 gfx/thebes/src/gfxQtNativeRenderer.cpp
>--- a/gfx/thebes/src/gfxQtNativeRenderer.cpp	Mon Apr 19 13:31:03 2010 +0300
>+++ b/gfx/thebes/src/gfxQtNativeRenderer.cpp	Mon Apr 19 18:18:07 2010 +0300
>@@ -31,23 +31,72 @@
>  * decision by deleting the provisions above and replace them with the notice
>  * and other provisions required by the GPL or the LGPL. If you do not delete
>  * the provisions above, a recipient may use your version of this file under
>  * the terms of any one of the MPL, the GPL or the LGPL.
>  *
>  * ***** END LICENSE BLOCK ***** */
> 
> #include <QWidget>
>+#include <QX11Info>
>+#include <QPainter>

QPainter is not used.

>+#include "cairo-qpainter.h"

nor cairo-qpainter.h

>+static Visual *
>+GetVisualByDepth(Display *aDisplay, int aDepth)

XMatchVisualInfo is already available to do this.
(Sorry, I forgot about that.)
http://hg.mozilla.org/mozilla-central/annotate/9585e4ed630e/layout/generic/nsObjectFrame.cpp#l5145

> nsresult
> gfxQtNativeRenderer::Draw(gfxContext* ctx, int width, int height,
>                           PRUint32 flags, DrawOutput* output)
> {
>+    nsresult result = NS_ERROR_NOT_IMPLEMENTED;

Declare the nsresult where it is first used in the return value from
NativeDraw.  Convention is to call the variable |rv|.

>+    ctx->NewPath();
>+    ctx->SetSource(xsurf);
>+    ctx->Paint();

IIUC NewPath is not necessary.

>+nsPluginInstanceOwner::Renderer::NativeDraw(gfxXlibSurface * xsurface,
>                                             short offsetX, short offsetY,
>                                             QRect * clipRects,
>                                             PRUint32 numClipRects)
> {
> #ifdef MOZ_X11
>+  Display *display = xsurface->XDisplay();
>+  Visual * visual = cairo_xlib_surface_get_visual(xsurface->CairoSurface());
>+  Screen *screen = cairo_xlib_surface_get_screen(xsurface->CairoSurface());
>+  Colormap colormap = QX11Info().colormap();

QX11Info().colormap() is good when the visual == QX11Info().visual() but is
not right when the depth is 32 (transparent).

I suggest creating and freeing a colormap in gfxQtNativeRenderer::Draw() only when !isOpaque, and passing QX11Info().colormap() when isOpaque.  (If it becomes a performance issue then
we can consider caching a colormap in the future.)
Attachment #439944 - Flags: review+ → review-
Attachment #439889 - Flags: review?(karlt) → review+
Comment on attachment 437919 [details] [diff] [review]
Fast get image from XSurface with XShmGetImage

Removing review request on the XShmGetImage patch as this is now obsolete.

If we are going to use XShm then I think we need to find a single place to have the XShm code rather than have multiple copies of similar code.  I suspect the best single place is in cairo.
Attachment #437919 - Flags: review?(karlt)
Attached patch NativeRenderer v3. (obsolete) — Splinter Review
Attachment #439944 - Attachment is obsolete: true
Attachment #440128 - Flags: review?(karlt)
Comment on attachment 440128 [details] [diff] [review]
NativeRenderer v3.

>+static Visual *
>+GetVisualByDepth(Display *aDisplay, Screen *aScreen, int aDepth)

This can be removed, now.

> nsresult
> gfxQtNativeRenderer::Draw(gfxContext* ctx, int width, int height,
>                           PRUint32 flags, DrawOutput* output)
> {
>+    Display *dpy = QX11Info().display();
>+    PRBool isOpaque = (flags & DRAW_IS_OPAQUE) ? PR_TRUE : PR_FALSE;
>+    Screen *screen = DefaultScreenOfDisplay(dpy);

I'm guessing QX11Info().screen() is the right thing to use here.

>+    int depth = QX11Info().depth();
>+    Visual *visual = (Visual*)QX11Info().visual();

I prefer static_cast<Visual*>().
It makes it clear that QX11Info().visual() is not returning an XID.

>+    Colormap colormap = QX11Info().colormap();
>+    PRBool allocColormap = PR_FALSE;
>+
>+    if (!isOpaque) {
>+        depth = 32;
>+        XVisualInfo vinfo;
>+        int foundVisual = XMatchVisualInfo(dpy, QX11Info().screen(),
>+                                           depth, TrueColor,
>+                                           &vinfo);

This can use the local variable |screen|.

>+        if (visual != vinfo.visual) {
>+            allocColormap = PR_TRUE;
>+            colormap = XCreateColormap(dpy,
>+                                       RootWindowOfScreen(screen),
>+                                       visual, AllocNone);
>+        }
>+        visual = vinfo.visual;

This is the visual that you want in XCreateColormap, so move the assignment to before XCreateColormap.

>+    nsresult rv = NativeDraw(xsurf.get(), colormap, 0, 0, NULL, 0);
>+    NS_ENSURE_SUCCESS(rv, rv);

Make the early return obvious:

  if (NS_FAILED(rv))
      return rv;

>+    if (!allocColormap)
>+        XFreeColormap(dpy, colormap);

And move this to before the early return.
Attachment #440128 - Flags: review?(karlt) → review-
Attachment #437919 - Attachment is obsolete: true
Attachment #440128 - Attachment is obsolete: true
Attachment #440138 - Flags: review?(karlt)
Attachment #440138 - Flags: review?(karlt) → review+
Pushed
http://hg.mozilla.org/mozilla-central/rev/beebc4d09baa
Status: ASSIGNED → RESOLVED
Closed: 14 years ago
Resolution: --- → FIXED
Product: Core → Core Graveyard
You need to log in before you can comment on or make changes to this bug.

Attachment

General

Creator:
Created:
Updated:
Size: