Bug 797431 - Add a flags parameter to PaintWindow. r=roc
authorMatt Woodrow <mwoodrow@mozilla.com>
Mon, 15 Oct 2012 17:53:37 +1300
changeset 118183 ab00790e8fedd734508a739b982af34c08a1a238
parent 118182 8dd63acc9c4fbde8bc371c06b10adb81c132defa
child 118184 1bca31fd0e58c29bfdfb713321f55a4078ae489b
push id1997
push userakeybl@mozilla.com
push dateMon, 07 Jan 2013 21:25:26 +0000
treeherdermozilla-beta@4baf45cdcf21 [default view] [failures only]
perfherder[talos] [build metrics] [platform microbench] (compared to previous push)
reviewersroc
bugs797431
milestone19.0a1
first release with
nightly linux32
nightly linux64
nightly mac
nightly win32
nightly win64
last release without
nightly linux32
nightly linux64
nightly mac
nightly win32
nightly win64
Bug 797431 - Add a flags parameter to PaintWindow. r=roc
view/src/nsView.cpp
view/src/nsView.h
view/src/nsViewManager.cpp
view/src/nsViewManager.h
widget/android/nsWindow.cpp
widget/cocoa/nsChildView.mm
widget/gonk/nsWindow.cpp
widget/gtk2/nsWindow.cpp
widget/nsIWidgetListener.h
widget/qt/nsWindow.cpp
widget/windows/nsWindowGfx.cpp
widget/xpwidgets/PuppetWidget.cpp
--- a/view/src/nsView.cpp
+++ b/view/src/nsView.cpp
@@ -1025,20 +1025,20 @@ nsView::RequestWindowClose(nsIWidget* aW
 
 void
 nsView::WillPaintWindow(nsIWidget* aWidget, bool aWillSendDidPaint)
 {
   mViewManager->WillPaintWindow(aWidget, aWillSendDidPaint);
 }
 
 bool
-nsView::PaintWindow(nsIWidget* aWidget, nsIntRegion aRegion, bool aSentWillPaint, bool aWillSendDidPaint)
+nsView::PaintWindow(nsIWidget* aWidget, nsIntRegion aRegion, uint32_t aFlags)
 {
   nsCOMPtr<nsViewManager> vm = mViewManager;
-  return vm->PaintWindow(aWidget, aRegion, aSentWillPaint, aWillSendDidPaint);
+  return vm->PaintWindow(aWidget, aRegion, aFlags);
 }
 
 void
 nsView::DidPaintWindow()
 {
   mViewManager->DidPaintWindow();
 }
 
--- a/view/src/nsView.h
+++ b/view/src/nsView.h
@@ -163,17 +163,17 @@ public:
 
   // nsIWidgetListener
   virtual nsIPresShell* GetPresShell();
   virtual nsIView* GetView() { return this; }
   bool WindowMoved(nsIWidget* aWidget, int32_t x, int32_t y);
   bool WindowResized(nsIWidget* aWidget, int32_t aWidth, int32_t aHeight);
   bool RequestWindowClose(nsIWidget* aWidget);
   void WillPaintWindow(nsIWidget* aWidget, bool aWillSendDidPaint);
-  bool PaintWindow(nsIWidget* aWidget, nsIntRegion aRegion, bool aSentDidPaint, bool aWillSendDidPaint);
+  bool PaintWindow(nsIWidget* aWidget, nsIntRegion aRegion, uint32_t aFlags);
   void DidPaintWindow();
   nsEventStatus HandleEvent(nsGUIEvent* aEvent, bool aUseAttachedEvents);
 
   virtual ~nsView();
 
   nsPoint GetOffsetTo(const nsView* aOther) const;
   nsIWidget* GetNearestWidget(nsPoint* aOffset) const;
   nsPoint GetOffsetTo(const nsView* aOther, const int32_t aAPD) const;
--- a/view/src/nsViewManager.cpp
+++ b/view/src/nsViewManager.cpp
@@ -678,33 +678,33 @@ void nsViewManager::WillPaintWindow(nsIW
 
   nsCOMPtr<nsIPresShell> shell = mPresShell;
   if (shell) {
     shell->WillPaintWindow(aWillSendDidPaint);
   }
 }
 
 bool nsViewManager::PaintWindow(nsIWidget* aWidget, nsIntRegion aRegion,
-                                bool aSentWillPaint, bool aWillSendDidPaint)
+                                uint32_t aFlags)
  {
   if (!aWidget || !mContext)
     return false;
 
   NS_ASSERTION(IsPaintingAllowed(),
                "shouldn't be receiving paint events while painting is disallowed!");
 
-  if (!aSentWillPaint && !IsRefreshDriverPaintingEnabled()) {
-    WillPaintWindow(aWidget, aWillSendDidPaint);
+  if (!(aFlags & nsIWidgetListener::SENT_WILL_PAINT) && !IsRefreshDriverPaintingEnabled()) {
+    WillPaintWindow(aWidget, (aFlags & nsIWidgetListener::WILL_SEND_DID_PAINT));
   }
 
   // Get the view pointer here since NS_WILL_PAINT might have
   // destroyed it during CallWillPaintOnObservers (bug 378273).
   nsView* view = nsView::GetViewFor(aWidget);
   if (view && !aRegion.IsEmpty()) {
-    Refresh(view, aRegion, aWillSendDidPaint);
+    Refresh(view, aRegion, (aFlags & nsIWidgetListener::WILL_SEND_DID_PAINT));
   }
 
   return true;
 }
 
 void nsViewManager::DidPaintWindow()
 {
   nsCOMPtr<nsIPresShell> shell = mPresShell;
--- a/view/src/nsViewManager.h
+++ b/view/src/nsViewManager.h
@@ -165,17 +165,17 @@ public: // NOT in nsIViewManager, so pri
 
   // Whether synchronous painting is allowed at the moment. For example,
   // widget geometry changes can cause synchronous painting, so they need to
   // be deferred while refresh is disabled.
   bool IsPaintingAllowed() { return RootViewManager()->mRefreshDisableCount == 0; }
 
   void WillPaintWindow(nsIWidget* aWidget, bool aWillSendDidPaint);
   bool PaintWindow(nsIWidget* aWidget, nsIntRegion aRegion,
-                   bool aSentWillPaint, bool aWillSendDidPaint);
+                   uint32_t aFlags);
   void DidPaintWindow();
 
   // Call this when you need to let the viewmanager know that it now has
   // pending updates.
   void PostPendingUpdate();
 
   uint32_t AppUnitsPerDevPixel() const
   {
--- a/widget/android/nsWindow.cpp
+++ b/widget/android/nsWindow.cpp
@@ -1004,17 +1004,17 @@ nsWindow::DrawTo(gfxASurface *targetSurf
 
                 nsRefPtr<gfxContext> ctx = new gfxContext(targetSurface);
 
                 {
                     mozilla::layers::RenderTraceScope trace2("Basic DrawTo", "727272");
                     AutoLayerManagerSetup
                       setupLayerManager(this, ctx, mozilla::layers::BUFFER_NONE);
 
-                    painted = mWidgetListener->PaintWindow(this, region, false, false);
+                    painted = mWidgetListener->PaintWindow(this, region, 0);
                 }
 
                 // XXX uhh.. we can't just ignore this because we no longer have
                 // what we needed before, but let's keep drawing the children anyway?
 #if 0
                 if (!painted)
                     return false;
 #endif
@@ -1024,17 +1024,17 @@ nsWindow::DrawTo(gfxASurface *targetSurf
                 break;
             }
 
             case mozilla::layers::LAYERS_OPENGL: {
 
                 static_cast<mozilla::layers::LayerManagerOGL*>(GetLayerManager(nullptr))->
                     SetClippingRegion(nsIntRegion(boundsRect));
 
-                painted = mWidgetListener->PaintWindow(this, region, false, false);
+                painted = mWidgetListener->PaintWindow(this, region, 0);
                 break;
             }
 
             default:
                 NS_ERROR("Invalid layer manager");
         }
 
         // We had no covering child, so make sure we draw all the children,
--- a/widget/cocoa/nsChildView.mm
+++ b/widget/cocoa/nsChildView.mm
@@ -1434,17 +1434,17 @@ bool nsChildView::PaintWindow(nsIntRegio
   }
 
   if (!listener)
     return false;
 
   bool returnValue = false;
   bool oldDispatchPaint = mIsDispatchPaint;
   mIsDispatchPaint = true;
-  returnValue = listener->PaintWindow(widget, aRegion, true, false);
+  returnValue = listener->PaintWindow(widget, aRegion, SENT_WILL_PAINT);
   mIsDispatchPaint = oldDispatchPaint;
   return returnValue;
 }
 
 #pragma mark -
 
 void nsChildView::ReportMoveEvent()
 {
--- a/widget/gonk/nsWindow.cpp
+++ b/widget/gonk/nsWindow.cpp
@@ -245,17 +245,17 @@ nsWindow::DoDraw(void)
 
     LayerManager* lm = gWindowToRedraw->GetLayerManager();
     if (mozilla::layers::LAYERS_OPENGL == lm->GetBackendType()) {
         LayerManagerOGL* oglm = static_cast<LayerManagerOGL*>(lm);
         oglm->SetClippingRegion(region);
         oglm->SetWorldTransform(sRotationMatrix);
 
         if (nsIWidgetListener* listener = gWindowToRedraw->GetWidgetListener())
-          listener->PaintWindow(gWindowToRedraw, region, false, false);
+          listener->PaintWindow(gWindowToRedraw, region, 0);
     } else if (mozilla::layers::LAYERS_BASIC == lm->GetBackendType()) {
         MOZ_ASSERT(sFramebufferOpen || sUsingOMTC);
         nsRefPtr<gfxASurface> targetSurface;
 
         if(sUsingOMTC)
             targetSurface = sOMTCSurface;
         else
             targetSurface = Framebuffer::BackBuffer();
@@ -266,17 +266,17 @@ nsWindow::DoDraw(void)
             ctx->Clip();
 
             // No double-buffering needed.
             AutoLayerManagerSetup setupLayerManager(
                 gWindowToRedraw, ctx, mozilla::layers::BUFFER_NONE,
                 ScreenRotation(EffectiveScreenRotation()));
 
             if (nsIWidgetListener* listener = gWindowToRedraw->GetWidgetListener())
-              listener->PaintWindow(gWindowToRedraw, region, false, false);
+              listener->PaintWindow(gWindowToRedraw, region, 0);
         }
 
         if (!sUsingOMTC) {
             targetSurface->Flush();
             Framebuffer::Present(region);
         }
     } else {
         NS_RUNTIMEABORT("Unexpected layer manager type");
--- a/widget/gtk2/nsWindow.cpp
+++ b/widget/gtk2/nsWindow.cpp
@@ -2116,31 +2116,31 @@ nsWindow::OnExposeEvent(cairo_t *cr)
         nsRefPtr<gfxContext> ctx = new gfxContext(GetThebesSurface());
 #else
         nsRefPtr<gfxContext> ctx = new gfxContext(GetThebesSurface(cr));
 #endif
         nsBaseWidget::AutoLayerManagerSetup
           setupLayerManager(this, ctx, mozilla::layers::BUFFER_NONE);
 
         if (mWidgetListener)
-            mWidgetListener->PaintWindow(this, region, true, true);
+            mWidgetListener->PaintWindow(this, region, nsIWidgetListener::SENT_WILL_PAINT | nsIWidgetListener::WILL_SEND_DID_PAINT);
 
         g_free(rects);
 
         if (mWidgetListener)
             mWidgetListener->DidPaintWindow();
 
         return TRUE;
 
     } else if (GetLayerManager()->GetBackendType() == mozilla::layers::LAYERS_OPENGL) {
         LayerManagerOGL *manager = static_cast<LayerManagerOGL*>(GetLayerManager());
         manager->SetClippingRegion(region);
 
         if (mWidgetListener)
-            mWidgetListener->PaintWindow(this, region, true, true);
+            mWidgetListener->PaintWindow(this, region, nsIWidgetListener::SENT_WILL_PAINT | nsIWidgetListener::WILL_SEND_DID_PAINT);
 
         g_free(rects);
 
         if (mWidgetListener)
             mWidgetListener->DidPaintWindow();
 
         return TRUE;
     }
@@ -2198,17 +2198,17 @@ nsWindow::OnExposeEvent(cairo_t *cr)
 
 #endif // MOZ_X11
 
     bool painted = false;
     {
       AutoLayerManagerSetup setupLayerManager(this, ctx, layerBuffering);
 
       if (mWidgetListener)
-        painted = mWidgetListener->PaintWindow(this, region, true, true);
+        painted = mWidgetListener->PaintWindow(this, region, nsIWidgetListener::SENT_WILL_PAINT | nsIWidgetListener::WILL_SEND_DID_PAINT);
     }
 
 #ifdef MOZ_X11
     // PaintWindow can Destroy us (bug 378273), avoid doing any paint
     // operations below if that happened - it will lead to XError and exit().
     if (shaped) {
         if (NS_LIKELY(!mIsDestroyed)) {
             if (painted) {
--- a/widget/nsIWidgetListener.h
+++ b/widget/nsIWidgetListener.h
@@ -113,23 +113,24 @@ public:
   virtual bool RequestWindowClose(nsIWidget* aWidget) { return false; }
 
   /*
    * Indicate that a paint is about to occur on this window.
    */
   virtual void WillPaintWindow(nsIWidget* aWidget, bool aWillSendDidPaint) { }
 
   /**
-   * Paint the specified region of the window. If aSentWillPaint is true,
-   * then WillPaintWindow has already been called. If aWillSendDidPaint is true,
-   * then a call to DidPaintWindow will be made afterwards. Returns true if the
+   * Paint the specified region of the window. Returns true if the
    * notification was handled.
    */
-  virtual bool PaintWindow(nsIWidget* aWidget, nsIntRegion aRegion,
-                           bool aSentWillPaint, bool aWillSendDidPaint) { return false; }
+  enum {
+    SENT_WILL_PAINT = 1 << 0, /* WillPaintWindow has already been called */
+    WILL_SEND_DID_PAINT = 1 << 1, /* A call to DidPaintWindow will be made afterwards. */
+  };
+  virtual bool PaintWindow(nsIWidget* aWidget, nsIntRegion aRegion, uint32_t aFlags) { return false; }
 
   /**
    * On some platforms, indicates that a paint occurred.
    */
   virtual void DidPaintWindow() { }
 
   /**
    * Handle an event.
--- a/widget/qt/nsWindow.cpp
+++ b/widget/qt/nsWindow.cpp
@@ -1042,17 +1042,17 @@ nsWindow::DoPaint(QPainter* aPainter, co
         // This is needed for rotate transformation on MeeGo
         // This will work very slow if pixman does not handle rotation very well
         matr.Rotate((M_PI/180) * gOrientationFilter.GetWindowRotationAngle());
         static_cast<mozilla::layers::LayerManagerOGL*>(GetLayerManager(nullptr))->
             SetWorldTransform(matr);
 #endif //MOZ_ENABLE_QTMOBILITY
 
         if (mWidgetListener)
-          painted = mWidgetListener->PaintWindow(this, region, true, true);
+          painted = mWidgetListener->PaintWindow(this, region, nsIWidgetListener::SENT_WILL_PAINT | nsIWidgetListener::WILL_SEND_DID_PAINT);
         aPainter->endNativePainting();
         if (mWidgetListener)
           mWidgetListener->DidPaintWindow();
         return painted;
     }
 
     gfxQtPlatform::RenderMode renderMode = gfxQtPlatform::GetPlatform()->GetRenderMode();
     int depth = aPainter->device()->depth();
@@ -1100,17 +1100,17 @@ nsWindow::DoPaint(QPainter* aPainter, co
       ctx->SetMatrix(matr);
     }
 
     {
         AutoLayerManagerSetup
             setupLayerManager(this, ctx, mozilla::layers::BUFFER_NONE);
         if (mWidgetListener) {
           nsIntRegion region(rect);
-          painted = mWidgetListener->PaintWindow(this, region, true, true);
+          painted = mWidgetListener->PaintWindow(this, region, nsIWidgetListener::SENT_WILL_PAINT | nsIWidgetListener::WILL_SEND_DID_PAINT);
         }
     }
 
     // DispatchEvent can Destroy us (bug 378273), avoid doing any paint
     // operations below if that happened - it will lead to XError and exit().
     if (NS_UNLIKELY(mIsDestroyed))
         return painted;
 
--- a/widget/windows/nsWindowGfx.cpp
+++ b/widget/windows/nsWindowGfx.cpp
@@ -411,17 +411,17 @@ bool nsWindow::OnPaint(HDC aDC, uint32_t
 #else
             doubleBuffering = mozilla::layers::BUFFER_BUFFERED;
 #endif
           }
 
           {
             AutoLayerManagerSetup
                 setupLayerManager(this, thebesContext, doubleBuffering);
-            result = listener->PaintWindow(this, region, true, true);
+            result = listener->PaintWindow(this, region, nsIWidgetListener::SENT_WILL_PAINT | nsIWidgetListener::WILL_SEND_DID_PAINT);
           }
 
 #ifdef MOZ_XUL
           if ((IsRenderMode(gfxWindowsPlatform::RENDER_GDI) ||
                IsRenderMode(gfxWindowsPlatform::RENDER_DIRECT2D))&&
               eTransparencyTransparent == mTransparencyMode) {
             // Data from offscreen drawing surface was copied to memory bitmap of transparent
             // bitmap. Now it can be read from memory bitmap to apply alpha channel and after
@@ -526,25 +526,25 @@ bool nsWindow::OnPaint(HDC aDC, uint32_t
                             SRCCOPY);
             }
           }
         }
         break;
       case LAYERS_OPENGL:
         static_cast<mozilla::layers::LayerManagerOGL*>(GetLayerManager())->
           SetClippingRegion(region);
-        result = listener->PaintWindow(this, region, true, true);
+        result = listener->PaintWindow(this, region, nsIWidgetListener::SENT_WILL_PAINT | nsIWidgetListener::WILL_SEND_DID_PAINT);
         break;
 #ifdef MOZ_ENABLE_D3D9_LAYER
       case LAYERS_D3D9:
         {
           LayerManagerD3D9 *layerManagerD3D9 =
             static_cast<mozilla::layers::LayerManagerD3D9*>(GetLayerManager());
           layerManagerD3D9->SetClippingRegion(region);
-          result = listener->PaintWindow(this, region, true, true);
+          result = listener->PaintWindow(this, region, nsIWidgetListener::SENT_WILL_PAINT | nsIWidgetListener::WILL_SEND_DID_PAINT);
           if (layerManagerD3D9->DeviceWasRemoved()) {
             mLayerManager->Destroy();
             mLayerManager = nullptr;
             // When our device was removed, we should have gfxWindowsPlatform
             // check if its render mode is up to date!
             gfxWindowsPlatform::GetPlatform()->UpdateRenderMode();
             Invalidate();
           }
@@ -554,17 +554,17 @@ bool nsWindow::OnPaint(HDC aDC, uint32_t
 #ifdef MOZ_ENABLE_D3D10_LAYER
       case LAYERS_D3D10:
         {
           gfxWindowsPlatform::GetPlatform()->UpdateRenderMode();
           LayerManagerD3D10 *layerManagerD3D10 = static_cast<mozilla::layers::LayerManagerD3D10*>(GetLayerManager());
           if (layerManagerD3D10->device() != gfxWindowsPlatform::GetPlatform()->GetD3D10Device()) {
             Invalidate();
           } else {
-            result = listener->PaintWindow(this, region, true, true);
+            result = listener->PaintWindow(this, region, nsIWidgetListener::SENT_WILL_PAINT | nsIWidgetListener::WILL_SEND_DID_PAINT);
           }
         }
         break;
 #endif
       default:
         NS_ERROR("Unknown layers backend used!");
         break;
     }
--- a/widget/xpwidgets/PuppetWidget.cpp
+++ b/widget/xpwidgets/PuppetWidget.cpp
@@ -505,24 +505,24 @@ PuppetWidget::Paint()
 
   {
 #ifdef DEBUG
     debug_DumpPaintEvent(stderr, this, region,
                          nsAutoCString("PuppetWidget"), 0);
 #endif
 
     if (mozilla::layers::LAYERS_D3D10 == mLayerManager->GetBackendType()) {
-      mAttachedWidgetListener->PaintWindow(this, region, false, true);
+      mAttachedWidgetListener->PaintWindow(this, region, nsIWidgetListener::WILL_SEND_DID_PAINT);
     } else {
       nsRefPtr<gfxContext> ctx = new gfxContext(mSurface);
       ctx->Rectangle(gfxRect(0,0,0,0));
       ctx->Clip();
       AutoLayerManagerSetup setupLayerManager(this, ctx,
                                               BUFFER_NONE);
-      mAttachedWidgetListener->PaintWindow(this, region, false, true);
+      mAttachedWidgetListener->PaintWindow(this, region, nsIWidgetListener::WILL_SEND_DID_PAINT);
       mTabChild->NotifyPainted();
     }
   }
 
   mAttachedWidgetListener->DidPaintWindow();
 
   return NS_OK;
 }