Bug 651017, part 4: deCOM nsIDeviceContext; include-minimization on nsDeviceContext.h itself; merge GetPrintDC() into Windows/OS/2 specific code; merge Shutdown() with ClearCachedSystemFonts(). Most references outside gfx not fixed up.
authorZack Weinberg <zackw@panix.com>
Sat, 16 Apr 2011 18:22:42 -0700
changeset 68552 3487552eaf91f81f15dfe5b8f787a1fea4730cb6
parent 68551 a353b9086b473283459a7f33c117cefe752e74d7
child 68553 3237cf9bc6f8e9573ca383e60fac07ad16fdba4c
push idunknown
push userunknown
push dateunknown
bugs651017
milestone6.0a1
Bug 651017, part 4: deCOM nsIDeviceContext; include-minimization on nsDeviceContext.h itself; merge GetPrintDC() into Windows/OS/2 specific code; merge Shutdown() with ClearCachedSystemFonts(). Most references outside gfx not fixed up.
gfx/layers/ThebesLayerBuffer.cpp
gfx/src/Makefile.in
gfx/src/nsDeviceContext.cpp
gfx/src/nsDeviceContext.h
gfx/src/nsFontMetrics.cpp
gfx/src/nsFontMetrics.h
gfx/src/nsGfxCIID.h
gfx/src/nsIDeviceContext.h
gfx/src/nsITheme.h
gfx/src/nsRect.cpp
gfx/src/nsRenderingContext.cpp
gfx/src/nsRenderingContext.h
gfx/src/nsSystemFontsAndroid.h
gfx/src/nsSystemFontsGTK2.h
gfx/src/nsSystemFontsMac.h
gfx/src/nsSystemFontsOS2.h
gfx/src/nsSystemFontsQt.h
gfx/src/nsSystemFontsWin.h
gfx/src/nsThebesDeviceContext.cpp
gfx/src/nsThebesDeviceContext.h
gfx/src/nsThebesGfxFactory.cpp
gfx/thebes/gfxTypes.h
layout/base/nsDocumentViewer.cpp
layout/base/nsPresContext.cpp
layout/printing/nsPrintEngine.cpp
widget/src/gtk2/nsNativeThemeGTK.cpp
widget/src/gtk2/nsWindow.cpp
widget/src/qt/nsWindow.cpp
widget/src/xpwidgets/nsBaseWidget.cpp
--- a/gfx/layers/ThebesLayerBuffer.cpp
+++ b/gfx/layers/ThebesLayerBuffer.cpp
@@ -35,17 +35,17 @@
  *
  * ***** END LICENSE BLOCK ***** */
 
 #include "ThebesLayerBuffer.h"
 #include "Layers.h"
 #include "gfxContext.h"
 #include "gfxPlatform.h"
 #include "gfxUtils.h"
-#include "nsIDeviceContext.h"
+#include "nsDeviceContext.h"
 
 namespace mozilla {
 namespace layers {
 
 static nsIntSize
 ScaledSize(const nsIntSize& aSize, float aXScale, float aYScale)
 {
   if (aXScale == 1.0 && aYScale == 1.0) {
@@ -184,17 +184,17 @@ MovePixels(gfxASurface* aBuffer,
 
 #ifdef DEBUG
   // If we're doing a self-copy, enforce that the rects we're copying
   // were computed in order to round to device pixels.  If the rects
   // we're moving *weren't* computed to round, then glitches like
   // seaming are likely.  Assume that the precision of these
   // computations is 1 app unit, and toss in a fudge factor of 2.0.
   static const gfxFloat kPrecision =
-    1.0 / gfxFloat(nsIDeviceContext::AppUnitsPerCSSPixel());
+    1.0 / gfxFloat(nsDeviceContext::AppUnitsPerCSSPixel());
   // FIXME/bug 637852: we've decided to live with transient glitches
   // during fast-panning for the time being.
   NS_WARN_IF_FALSE(
     src.WithinEpsilonOfIntegerPixels(2.0 * kPrecision * aXResolution) &&
     dest.WithinEpsilonOfIntegerPixels(2.0 * kPrecision * aXResolution),
     "Rects don't round to device pixels within precision; glitches likely to follow");
 #endif
 
--- a/gfx/src/Makefile.in
+++ b/gfx/src/Makefile.in
@@ -79,17 +79,17 @@ EXPORTS	= \
 	nsRect.h \
 	nsRegion.h \
 	nsPoint.h \
 	nsSize.h \
 	nsMargin.h \
 	nsTransform2D.h \
 	nsRenderingContext.h \
 	nsFontMetrics.h \
-	nsIDeviceContext.h \
+	nsDeviceContext.h \
 	nsGfxCIID.h \
 	nsIRegion.h \
 	nsITheme.h \
 	nsThemeConstants.h \
 	nsBoundingMetrics.h \
 	$(NULL)
 
 ifdef MOZ_X11
@@ -99,17 +99,17 @@ endif
 CPPSRCS = \
         nsColor.cpp \
         nsFont.cpp \
         nsRect.cpp \
         nsRegion.cpp \
         nsTransform2D.cpp \
         nsScriptableRegion.cpp \
         gfxCrashReporterUtils.cpp \
-        nsThebesDeviceContext.cpp \
+        nsDeviceContext.cpp \
         nsThebesRegion.cpp \
         nsThebesGfxFactory.cpp \
         nsRenderingContext.cpp \
         nsFontMetrics.cpp \
         nsThebesFontEnumerator.cpp \
        $(NULL)
 
 ifdef MOZ_X11
rename from gfx/src/nsThebesDeviceContext.cpp
rename to gfx/src/nsDeviceContext.cpp
--- a/gfx/src/nsThebesDeviceContext.cpp
+++ b/gfx/src/nsDeviceContext.cpp
@@ -32,60 +32,50 @@
  * use your version of this file under the terms of the MPL, indicate your
  * 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 "nsFont.h"
-#include "nsGfxCIID.h"
+#include "nsDeviceContext.h"
+#include "nsCRT.h"
+#include "nsFontMetrics.h"
+#include "nsRenderingContext.h"
+#include "nsIView.h"
+#include "nsIWidget.h"
+
+#include "mozilla/Services.h"
+#include "nsIServiceManager.h"
 #include "nsILanguageAtomService.h"
-#include "nsUnicharUtils.h"
-
-#include "nsIServiceManager.h"
-#include "nsIPrefService.h"
 #include "nsIObserver.h"
 #include "nsIObserverService.h"
-#include "nsCRT.h"
-#include "mozilla/Services.h"
-
-#include "nsThebesDeviceContext.h"
-#include "nsRenderingContext.h"
-#include "gfxUserFontSet.h"
-#include "gfxPlatform.h"
-
-#include "nsIWidget.h"
-#include "nsIView.h"
-#include "nsILookAndFeel.h"
+#include "nsIPrefService.h"
 
 #include "gfxImageSurface.h"
 
 #ifdef MOZ_ENABLE_GTK2
 #include "nsSystemFontsGTK2.h"
 #include "gfxPDFSurface.h"
 #include "gfxPSSurface.h"
 static nsSystemFontsGTK2 *gSystemFonts = nsnull;
 #elif XP_WIN
 #include "nsSystemFontsWin.h"
 #include "gfxWindowsSurface.h"
 #include "gfxPDFSurface.h"
 static nsSystemFontsWin *gSystemFonts = nsnull;
-#ifndef WINCE
-#include <usp10.h>
-#endif
 #elif defined(XP_OS2)
 #include "nsSystemFontsOS2.h"
+#include "gfxOS2Surface.h"
 #include "gfxPDFSurface.h"
 static nsSystemFontsOS2 *gSystemFonts = nsnull;
 #elif XP_MACOSX
 #include "nsSystemFontsMac.h"
 #include "gfxQuartzSurface.h"
-#include "gfxImageSurface.h"
 static nsSystemFontsMac *gSystemFonts = nsnull;
 #elif defined(MOZ_WIDGET_QT)
 #include "nsSystemFontsQt.h"
 #include "gfxPDFSurface.h"
 static nsSystemFontsQt *gSystemFonts = nsnull;
 #elif defined(ANDROID)
 #include "nsSystemFontsAndroid.h"
 #include "gfxPDFSurface.h"
@@ -100,39 +90,39 @@ class nsFontCache : public nsIObserver
 {
 public:
     nsFontCache()   { MOZ_COUNT_CTOR(nsFontCache); }
     ~nsFontCache()  { MOZ_COUNT_DTOR(nsFontCache); }
 
     NS_DECL_ISUPPORTS
     NS_DECL_NSIOBSERVER
 
-    void Init(nsIDeviceContext* aContext);
+    void Init(nsDeviceContext* aContext);
     void Destroy();
 
     nsresult GetMetricsFor(const nsFont& aFont, nsIAtom* aLanguage,
                            gfxUserFontSet* aUserFontSet,
                            nsFontMetrics*& aMetrics);
 
     void FontMetricsDeleted(const nsFontMetrics* aFontMetrics);
     void Compact();
     void Flush();
 
 protected:
-    nsIDeviceContext*         mContext; // owner
+    nsDeviceContext*          mContext; // owner
     nsTArray<nsFontMetrics*>  mFontMetrics;
 };
 
 NS_IMPL_ISUPPORTS1(nsFontCache, nsIObserver)
 
 // The Init and Destroy methods are necessary because it's not
 // safe to call AddObserver from a constructor or RemoveObserver
 // from a destructor.  That should be fixed.
 void
-nsFontCache::Init(nsIDeviceContext* aContext)
+nsFontCache::Init(nsDeviceContext* aContext)
 {
     mContext = aContext;
     // register as a memory-pressure observer to free font resources
     // in low-memory situations.
     nsCOMPtr<nsIObserverService> obs = GetObserverService();
     if (obs)
         obs->AddObserver(this, "memory-pressure", PR_FALSE);
 }
@@ -261,95 +251,91 @@ nsFontCache::Flush()
         // won't waste time in triggering the notification of
         // FontMetricsDeleted() in the subsequent release
         fm->Destroy();
         NS_RELEASE(fm);
     }
     mFontMetrics.Clear();
 }
 
-NS_IMPL_ISUPPORTS1(nsThebesDeviceContext, nsIDeviceContext)
-
-nsThebesDeviceContext::nsThebesDeviceContext()
+nsDeviceContext::nsDeviceContext()
+    : mWidth(0), mHeight(0), mDepth(0),
+      mAppUnitsPerDevPixel(-1), mAppUnitsPerDevNotScaledPixel(-1),
+      mAppUnitsPerPhysicalInch(-1),
+      mPixelScale(1.0f), mPrintingScale(1.0f),
+      mFontCache(nsnull)
 {
-    mAppUnitsPerDevPixel = nscoord(-1);
-    mAppUnitsPerPhysicalInch = nscoord(-1);
-    mAppUnitsPerDevNotScaledPixel = nscoord(-1);
-    mPixelScale = 1.0f;
-
-    mFontCache = nsnull;
-    mWidget = nsnull;
-
-    mDepth = 0;
-    mWidth = 0;
-    mHeight = 0;
-    mPrintingScale = 1.0f;
 }
 
 // Note: we use a bare pointer for mFontCache so that nsFontCache
-// can be an incomplete type in nsThebesDeviceContext.h.
+// can be an incomplete type in nsDeviceContext.h.
 // Therefore we have to do all the refcounting by hand.
-nsThebesDeviceContext::~nsThebesDeviceContext()
+nsDeviceContext::~nsDeviceContext()
 {
     if (mFontCache) {
         mFontCache->Destroy();
         NS_RELEASE(mFontCache);
     }
 }
 
-NS_IMETHODIMP nsThebesDeviceContext::CreateFontCache()
+void
+nsDeviceContext::CreateFontCache()
 {
     mFontCache = new nsFontCache();
     NS_ADDREF(mFontCache);
     mFontCache->Init(this);
     GetLocaleLanguage();
-    return NS_OK;
 }
 
-NS_IMETHODIMP nsThebesDeviceContext::FontMetricsDeleted(const nsFontMetrics* aFontMetrics)
+nsresult
+nsDeviceContext::FontMetricsDeleted(const nsFontMetrics* aFontMetrics)
 {
     if (mFontCache) {
         mFontCache->FontMetricsDeleted(aFontMetrics);
     }
     return NS_OK;
 }
 
 void
-nsThebesDeviceContext::GetLocaleLanguage(void)
+nsDeviceContext::GetLocaleLanguage(void)
 {
     if (!mLocaleLanguage) {
         nsCOMPtr<nsILanguageAtomService> langService;
         langService = do_GetService(NS_LANGUAGEATOMSERVICE_CONTRACTID);
         if (langService) {
             mLocaleLanguage = langService->GetLocaleLanguage();
         }
         if (!mLocaleLanguage) {
             mLocaleLanguage = do_GetAtom("x-western");
         }
     }
 }
 
-NS_IMETHODIMP nsThebesDeviceContext::GetMetricsFor(const nsFont& aFont,
-  nsIAtom* aLanguage, gfxUserFontSet* aUserFontSet, nsFontMetrics*& aMetrics)
+nsresult
+nsDeviceContext::GetMetricsFor(const nsFont& aFont,
+                               nsIAtom* aLanguage,
+                               gfxUserFontSet* aUserFontSet,
+                               nsFontMetrics*& aMetrics)
 {
     if (!mFontCache)
         CreateFontCache();
 
     // XXX figure out why aLanguage is NULL sometimes
     //      -> see nsPageFrame.cpp:511
     if (!aLanguage) {
         aLanguage = mLocaleLanguage;
     }
 
     return mFontCache->GetMetricsFor(aFont, aLanguage, aUserFontSet, aMetrics);
 }
 
-NS_IMETHODIMP nsThebesDeviceContext::GetMetricsFor(const nsFont& aFont,
-                                                   gfxUserFontSet* aUserFontSet,
-                                                   nsFontMetrics*& aMetrics)
+nsresult
+nsDeviceContext::GetMetricsFor(const nsFont& aFont,
+                               gfxUserFontSet* aUserFontSet,
+                               nsFontMetrics*& aMetrics)
 {
     if (!mFontCache)
         CreateFontCache();
 
     return mFontCache->GetMetricsFor(aFont, mLocaleLanguage, aUserFontSet,
                                      aMetrics);
 }
 
@@ -361,94 +347,91 @@ struct FontEnumData {
 static PRBool
 FontEnumCallback(const nsString& aFamily, PRBool aGeneric, void *aData)
 {
     FontEnumData* data = (FontEnumData*)aData;
     data->mFaceName = aFamily;
     return PR_FALSE; // stop
 }
 
-NS_IMETHODIMP
-nsThebesDeviceContext::FirstExistingFont(const nsFont& aFont,
-                                         nsString& aFaceName)
+nsresult
+nsDeviceContext::FirstExistingFont(const nsFont& aFont,
+                                   nsString& aFaceName)
 {
     FontEnumData data(aFaceName);
     if (aFont.EnumerateFamilies(FontEnumCallback, &data)) {
         return NS_ERROR_FAILURE; // can only happen for an empty font
     }
     return NS_OK;
 }
 
-NS_IMETHODIMP
-nsThebesDeviceContext::GetLocalFontName(const nsString& aFaceName,
-                                        nsString& aLocalName,
-                                        PRBool& aAliased)
+nsresult
+nsDeviceContext::GetLocalFontName(const nsString& aFaceName,
+                                  nsString& aLocalName,
+                                  PRBool& aAliased)
 {
     aLocalName = aFaceName;
     aAliased = PR_FALSE;
     return NS_OK;
 }
 
-NS_IMETHODIMP nsThebesDeviceContext::FlushFontCache(void)
+nsresult
+nsDeviceContext::FlushFontCache(void)
 {
     if (mFontCache)
         mFontCache->Flush();
     return NS_OK;
 }
 
-/* static */ void
-nsThebesDeviceContext::Shutdown()
+PRBool
+nsDeviceContext::IsPrinterSurface()
 {
-    delete gSystemFonts;
-    gSystemFonts = nsnull;
+    return(mPrintingSurface != NULL);
 }
 
-PRBool
-nsThebesDeviceContext::IsPrinterSurface()
-{
-  return(mPrintingSurface != NULL);
-}
-
-nsresult
-nsThebesDeviceContext::SetDPI()
+void
+nsDeviceContext::SetDPI()
 {
     float dpi = -1.0f;
 
     // PostScript, PDF and Mac (when printing) all use 72 dpi
     // Use a printing DC to determine the other dpi values
     if (mPrintingSurface) {
         switch (mPrintingSurface->GetType()) {
-            case gfxASurface::SurfaceTypePDF:
-            case gfxASurface::SurfaceTypePS:
-            case gfxASurface::SurfaceTypeQuartz:
-                dpi = 72.0f;
-                break;
+        case gfxASurface::SurfaceTypePDF:
+        case gfxASurface::SurfaceTypePS:
+        case gfxASurface::SurfaceTypeQuartz:
+            dpi = 72.0f;
+            break;
 #ifdef XP_WIN
-            case gfxASurface::SurfaceTypeWin32:
-            case gfxASurface::SurfaceTypeWin32Printing: {
-                PRInt32 OSVal = GetDeviceCaps(GetPrintHDC(), LOGPIXELSY);
-                dpi = 144.0f;
-                mPrintingScale = float(OSVal) / dpi;
-                break;
-            }
+        case gfxASurface::SurfaceTypeWin32:
+        case gfxASurface::SurfaceTypeWin32Printing: {
+            HDC dc = reinterpret_cast<gfxWindowsSurface*>(mPrintingSurface.get())->GetDC();
+            PRInt32 OSVal = GetDeviceCaps(dc, LOGPIXELSY);
+            dpi = 144.0f;
+            mPrintingScale = float(OSVal) / dpi;
+            break;
+        }
 #endif
 #ifdef XP_OS2
-            case gfxASurface::SurfaceTypeOS2:
-                LONG lDPI;
-                if (DevQueryCaps(GetPrintHDC(), CAPS_VERTICAL_FONT_RES, 1, &lDPI))
-                    dpi = lDPI;
-                break;
+        case gfxASurface::SurfaceTypeOS2: {
+            LONG lDPI;
+            HDC dc = GpiQueryDevice(reinterpret_cast<gfxOS2Surface*>(mPrintingSurface.get())->GetPS());
+            if (DevQueryCaps(dc, CAPS_VERTICAL_FONT_RES, 1, &lDPI))
+                dpi = lDPI;
+            break;
+        }
 #endif
-            default:
-                NS_NOTREACHED("Unexpected printing surface type");
-                break;
+        default:
+            NS_NOTREACHED("Unexpected printing surface type");
+            break;
         }
 
         mAppUnitsPerDevNotScaledPixel =
-          NS_lround((AppUnitsPerCSSPixel() * 96) / dpi);
+            NS_lround((AppUnitsPerCSSPixel() * 96) / dpi);
     } else {
         nsCOMPtr<nsIPrefBranch> prefs = do_GetService(NS_PREFSERVICE_CONTRACTID);
 
         // A value of -1 means use the maximum of 96 and the system DPI.
         // A value of 0 means use the system DPI. A positive value is used as the DPI.
         // This sets the physical size of a device pixel and thus controls the
         // interpretation of physical units.
         PRInt32 prefDPI = -1;
@@ -495,54 +478,52 @@ nsThebesDeviceContext::SetDPI()
         mAppUnitsPerDevNotScaledPixel =
             PR_MAX(1, NS_lround(AppUnitsPerCSSPixel() / devPixelsPerCSSPixel));
     }
 
     NS_ASSERTION(dpi != -1.0, "no dpi set");
 
     mAppUnitsPerPhysicalInch = NS_lround(dpi * mAppUnitsPerDevNotScaledPixel);
     UpdateScaledAppUnits();
-
-    return NS_OK;
 }
 
-NS_IMETHODIMP
-nsThebesDeviceContext::Init(nsIWidget *aWidget)
+nsresult
+nsDeviceContext::Init(nsIWidget *aWidget)
 {
     if (mScreenManager && mWidget == aWidget)
         return NS_OK;
 
     mWidget = aWidget;
     SetDPI();
 
     if (mScreenManager)
         return NS_OK;
 
     mScreenManager = do_GetService("@mozilla.org/gfx/screenmanager;1");
 
     return NS_OK;
 }
 
-NS_IMETHODIMP
-nsThebesDeviceContext::CreateRenderingContext(nsIView *aView,
-                                              nsRenderingContext *&aContext)
+nsresult
+nsDeviceContext::CreateRenderingContext(nsIView *aView,
+                                        nsRenderingContext *&aContext)
 {
     // This is currently only called by the caret code
     NS_ENSURE_ARG_POINTER(aView);
     NS_PRECONDITION(aView->HasWidget(), "View has no widget!");
 
     nsCOMPtr<nsIWidget> widget;
     widget = aView->GetWidget();
 
     return CreateRenderingContext(widget, aContext);
 }
 
-NS_IMETHODIMP
-nsThebesDeviceContext::CreateRenderingContext(nsIWidget *aWidget,
-                                              nsRenderingContext *&aContext)
+nsresult
+nsDeviceContext::CreateRenderingContext(nsIWidget *aWidget,
+                                        nsRenderingContext *&aContext)
 {
     nsresult rv;
 
     aContext = nsnull;
     nsRefPtr<nsRenderingContext> pContext;
     rv = CreateRenderingContextInstance(*getter_AddRefs(pContext));
     if (NS_SUCCEEDED(rv)) {
         nsRefPtr<gfxASurface> surface(aWidget->GetThebesSurface());
@@ -553,18 +534,18 @@ nsThebesDeviceContext::CreateRenderingCo
         } else {
             rv = NS_ERROR_FAILURE;
         }
     }
 
     return rv;
 }
 
-NS_IMETHODIMP
-nsThebesDeviceContext::CreateRenderingContext(nsRenderingContext *&aContext)
+nsresult
+nsDeviceContext::CreateRenderingContext(nsRenderingContext *&aContext)
 {
     nsresult rv = NS_OK;
 
     aContext = nsnull;
     nsRefPtr<nsRenderingContext> pContext;
     rv = CreateRenderingContextInstance(*getter_AddRefs(pContext));
     if (NS_SUCCEEDED(rv)) {
         if (mPrintingSurface) {
@@ -575,42 +556,40 @@ nsThebesDeviceContext::CreateRenderingCo
         } else {
             rv = NS_ERROR_FAILURE;
         }
     }
 
     return rv;
 }
 
-NS_IMETHODIMP
-nsThebesDeviceContext::CreateRenderingContextInstance(nsRenderingContext *&aContext)
+nsresult
+nsDeviceContext::CreateRenderingContextInstance(nsRenderingContext *&aContext)
 {
     nsRefPtr<nsRenderingContext> renderingContext = new nsRenderingContext();
     if (!renderingContext)
         return NS_ERROR_OUT_OF_MEMORY;
 
     aContext = renderingContext;
     NS_ADDREF(aContext);
 
     return NS_OK;
 }
 
-NS_IMETHODIMP
-nsThebesDeviceContext::ClearCachedSystemFonts()
+/* static */ void
+nsDeviceContext::ClearCachedSystemFonts()
 {
-    //clear our cache of stored system fonts
     if (gSystemFonts) {
         delete gSystemFonts;
         gSystemFonts = nsnull;
     }
-    return NS_OK;
 }
 
-NS_IMETHODIMP
-nsThebesDeviceContext::GetSystemFont(nsSystemFontID aID, nsFont *aFont) const
+nsresult
+nsDeviceContext::GetSystemFont(nsSystemFontID aID, nsFont *aFont) const
 {
     if (!gSystemFonts) {
 #ifdef MOZ_ENABLE_GTK2
         gSystemFonts = new nsSystemFontsGTK2();
 #elif XP_WIN
         gSystemFonts = new nsSystemFontsWin();
 #elif XP_OS2
         gSystemFonts = new nsSystemFontsOS2();
@@ -639,96 +618,96 @@ nsThebesDeviceContext::GetSystemFont(nsS
     aFont->decorations = NS_FONT_DECORATION_NONE;
     aFont->size = NSFloatPixelsToAppUnits(fontStyle.size, UnscaledAppUnitsPerDevPixel());
     //aFont->langGroup = fontStyle.langGroup;
     aFont->sizeAdjust = fontStyle.sizeAdjust;
 
     return rv;
 }
 
-NS_IMETHODIMP
-nsThebesDeviceContext::CheckFontExistence(const nsString& aFaceName)
+nsresult
+nsDeviceContext::CheckFontExistence(const nsString& aFaceName)
 {
     return NS_OK;
 }
 
-NS_IMETHODIMP
-nsThebesDeviceContext::GetDepth(PRUint32& aDepth)
+nsresult
+nsDeviceContext::GetDepth(PRUint32& aDepth)
 {
     if (mDepth == 0) {
         nsCOMPtr<nsIScreen> primaryScreen;
         mScreenManager->GetPrimaryScreen(getter_AddRefs(primaryScreen));
         primaryScreen->GetColorDepth(reinterpret_cast<PRInt32 *>(&mDepth));
     }
 
     aDepth = mDepth;
     return NS_OK;
 }
 
-NS_IMETHODIMP
-nsThebesDeviceContext::GetDeviceSurfaceDimensions(nscoord &aWidth, nscoord &aHeight)
+nsresult
+nsDeviceContext::GetDeviceSurfaceDimensions(nscoord &aWidth, nscoord &aHeight)
 {
     if (mPrintingSurface) {
         // we have a printer device
         aWidth = mWidth;
         aHeight = mHeight;
     } else {
         nsRect area;
         ComputeFullAreaUsingScreen(&area);
         aWidth = area.width;
         aHeight = area.height;
     }
 
     return NS_OK;
 }
 
-NS_IMETHODIMP
-nsThebesDeviceContext::GetRect(nsRect &aRect)
+nsresult
+nsDeviceContext::GetRect(nsRect &aRect)
 {
     if (mPrintingSurface) {
         // we have a printer device
         aRect.x = 0;
         aRect.y = 0;
         aRect.width = mWidth;
         aRect.height = mHeight;
     } else
         ComputeFullAreaUsingScreen ( &aRect );
 
     return NS_OK;
 }
 
-NS_IMETHODIMP
-nsThebesDeviceContext::GetClientRect(nsRect &aRect)
+nsresult
+nsDeviceContext::GetClientRect(nsRect &aRect)
 {
     if (mPrintingSurface) {
         // we have a printer device
         aRect.x = 0;
         aRect.y = 0;
         aRect.width = mWidth;
         aRect.height = mHeight;
     }
     else
         ComputeClientRectUsingScreen(&aRect);
 
     return NS_OK;
 }
 
-NS_IMETHODIMP
-nsThebesDeviceContext::PrepareNativeWidget(nsIWidget* aWidget, void** aOut)
+nsresult
+nsDeviceContext::PrepareNativeWidget(nsIWidget* aWidget, void** aOut)
 {
     *aOut = nsnull;
     return NS_OK;
 }
 
 
 /*
  * below methods are for printing
  */
-NS_IMETHODIMP
-nsThebesDeviceContext::InitForPrinting(nsIDeviceContextSpec *aDevice)
+nsresult
+nsDeviceContext::InitForPrinting(nsIDeviceContextSpec *aDevice)
 {
     NS_ENSURE_ARG_POINTER(aDevice);
 
     mDeviceContextSpec = aDevice;
 
     nsresult rv = aDevice->GetSurfaceForPrinter(getter_AddRefs(mPrintingSurface));
     if (NS_FAILED(rv))
         return NS_ERROR_FAILURE;
@@ -736,94 +715,94 @@ nsThebesDeviceContext::InitForPrinting(n
     Init(nsnull);
 
     CalcPrintingSize();
 
     return NS_OK;
 }
 
 
-NS_IMETHODIMP
-nsThebesDeviceContext::PrepareDocument(PRUnichar * aTitle,
-                                       PRUnichar*  aPrintToFileName)
+nsresult
+nsDeviceContext::PrepareDocument(PRUnichar * aTitle,
+                                 PRUnichar*  aPrintToFileName)
 {
     return NS_OK;
 }
 
 
-NS_IMETHODIMP
-nsThebesDeviceContext::BeginDocument(PRUnichar*  aTitle,
-                                     PRUnichar*  aPrintToFileName,
-                                     PRInt32     aStartPage,
-                                     PRInt32     aEndPage)
+nsresult
+nsDeviceContext::BeginDocument(PRUnichar*  aTitle,
+                               PRUnichar*  aPrintToFileName,
+                               PRInt32     aStartPage,
+                               PRInt32     aEndPage)
 {
     static const PRUnichar kEmpty[] = { '\0' };
     nsresult rv;
 
     rv = mPrintingSurface->BeginPrinting(nsDependentString(aTitle ? aTitle : kEmpty),
                                          nsDependentString(aPrintToFileName ? aPrintToFileName : kEmpty));
 
     if (NS_SUCCEEDED(rv) && mDeviceContextSpec)
         rv = mDeviceContextSpec->BeginDocument(aTitle, aPrintToFileName, aStartPage, aEndPage);
 
     return rv;
 }
 
 
-NS_IMETHODIMP
-nsThebesDeviceContext::EndDocument(void)
+nsresult
+nsDeviceContext::EndDocument(void)
 {
     nsresult rv = NS_OK;
 
     if (mPrintingSurface) {
         rv = mPrintingSurface->EndPrinting();
         if (NS_SUCCEEDED(rv))
             mPrintingSurface->Finish();
     }
 
     if (mDeviceContextSpec)
         mDeviceContextSpec->EndDocument();
 
     return rv;
 }
 
 
-NS_IMETHODIMP
-nsThebesDeviceContext::AbortDocument(void)
+nsresult
+nsDeviceContext::AbortDocument(void)
 {
     nsresult rv = mPrintingSurface->AbortPrinting();
 
     if (mDeviceContextSpec)
         mDeviceContextSpec->EndDocument();
 
     return rv;
 }
 
 
-NS_IMETHODIMP
-nsThebesDeviceContext::BeginPage(void)
+nsresult
+nsDeviceContext::BeginPage(void)
 {
     nsresult rv = NS_OK;
 
     if (mDeviceContextSpec)
         rv = mDeviceContextSpec->BeginPage();
 
     if (NS_FAILED(rv)) return rv;
 
-   /* We need to get a new surface for each page on the Mac */
+    /* We need to get a new surface for each page on the Mac */
 #ifdef XP_MACOSX
     mDeviceContextSpec->GetSurfaceForPrinter(getter_AddRefs(mPrintingSurface));
 #endif
     rv = mPrintingSurface->BeginPage();
 
     return rv;
 }
 
-NS_IMETHODIMP
-nsThebesDeviceContext::EndPage(void)
+nsresult
+nsDeviceContext::EndPage(void)
 {
     nsresult rv = mPrintingSurface->EndPage();
 
     /* We need to release the CGContextRef in the surface here, plus it's
        not something you would want anyway, as these CGContextRefs are only good
        for one page. */
 #ifdef XP_MACOSX
     mPrintingSurface = nsnull;
@@ -833,17 +812,17 @@ nsThebesDeviceContext::EndPage(void)
         mDeviceContextSpec->EndPage();
 
     return rv;
 }
 
 /** End printing methods **/
 
 void
-nsThebesDeviceContext::ComputeClientRectUsingScreen(nsRect* outRect)
+nsDeviceContext::ComputeClientRectUsingScreen(nsRect* outRect)
 {
     // we always need to recompute the clientRect
     // because the window may have moved onto a different screen. In the single
     // monitor case, we only need to do the computation if we haven't done it
     // once already, and remember that we have because we're assured it won't change.
     nsCOMPtr<nsIScreen> screen;
     FindScreen (getter_AddRefs(screen));
     if (screen) {
@@ -854,17 +833,17 @@ nsThebesDeviceContext::ComputeClientRect
         outRect->y = NSIntPixelsToAppUnits(y, AppUnitsPerDevPixel());
         outRect->x = NSIntPixelsToAppUnits(x, AppUnitsPerDevPixel());
         outRect->width = NSIntPixelsToAppUnits(width, AppUnitsPerDevPixel());
         outRect->height = NSIntPixelsToAppUnits(height, AppUnitsPerDevPixel());
     }
 }
 
 void
-nsThebesDeviceContext::ComputeFullAreaUsingScreen(nsRect* outRect)
+nsDeviceContext::ComputeFullAreaUsingScreen(nsRect* outRect)
 {
     // if we have more than one screen, we always need to recompute the clientRect
     // because the window may have moved onto a different screen. In the single
     // monitor case, we only need to do the computation if we haven't done it
     // once already, and remember that we have because we're assured it won't change.
     nsCOMPtr<nsIScreen> screen;
     FindScreen ( getter_AddRefs(screen) );
     if ( screen ) {
@@ -883,27 +862,27 @@ nsThebesDeviceContext::ComputeFullAreaUs
 }
 
 //
 // FindScreen
 //
 // Determines which screen intersects the largest area of the given surface.
 //
 void
-nsThebesDeviceContext::FindScreen(nsIScreen** outScreen)
+nsDeviceContext::FindScreen(nsIScreen** outScreen)
 {
     if (mWidget && mWidget->GetNativeData(NS_NATIVE_WINDOW))
         mScreenManager->ScreenForNativeWidget(mWidget->GetNativeData(NS_NATIVE_WINDOW),
                                               outScreen);
     else
         mScreenManager->GetPrimaryScreen(outScreen);
 }
 
 void
-nsThebesDeviceContext::CalcPrintingSize()
+nsDeviceContext::CalcPrintingSize()
 {
     if (!mPrintingSurface)
         return;
 
     PRBool inPoints = PR_TRUE;
 
     gfxSize size(0, 0);
     switch (mPrintingSurface->GetType()) {
@@ -931,113 +910,86 @@ nsThebesDeviceContext::CalcPrintingSize(
         inPoints = PR_TRUE; // this is really only true when we're printing
         size = reinterpret_cast<gfxQuartzSurface*>(mPrintingSurface.get())->GetSize();
         break;
 #endif
 
 #ifdef XP_WIN
     case gfxASurface::SurfaceTypeWin32:
     case gfxASurface::SurfaceTypeWin32Printing:
-    {
-        inPoints = PR_FALSE;
-        HDC dc =  GetPrintHDC();
-        if (!dc)
-            dc = GetDC((HWND)mWidget->GetNativeData(NS_NATIVE_WIDGET));
-        size.width = NSFloatPixelsToAppUnits(::GetDeviceCaps(dc, HORZRES)/mPrintingScale, AppUnitsPerDevPixel());
-        size.height = NSFloatPixelsToAppUnits(::GetDeviceCaps(dc, VERTRES)/mPrintingScale, AppUnitsPerDevPixel());
-        mDepth = (PRUint32)::GetDeviceCaps(dc, BITSPIXEL);
-        if (dc != (HDC)GetPrintHDC())
-            ReleaseDC((HWND)mWidget->GetNativeData(NS_NATIVE_WIDGET), dc);
-        break;
-    }
+        {
+            inPoints = PR_FALSE;
+            HDC dc = reinterpret_cast<gfxWindowsSurface*>(mPrintingSurface.get())->GetDC();
+            if (!dc)
+                dc = GetDC((HWND)mWidget->GetNativeData(NS_NATIVE_WIDGET));
+            size.width = NSFloatPixelsToAppUnits(::GetDeviceCaps(dc, HORZRES)/mPrintingScale, AppUnitsPerDevPixel());
+            size.height = NSFloatPixelsToAppUnits(::GetDeviceCaps(dc, VERTRES)/mPrintingScale, AppUnitsPerDevPixel());
+            mDepth = (PRUint32)::GetDeviceCaps(dc, BITSPIXEL);
+            if (dc != reinterpret_cast<gfxWindowsSurface*>(mPrintingSurface.get())->GetDC())
+                ReleaseDC((HWND)mWidget->GetNativeData(NS_NATIVE_WIDGET), dc);
+            break;
+        }
 #endif
 
 #ifdef XP_OS2
     case gfxASurface::SurfaceTypeOS2:
-    {
-        inPoints = PR_FALSE;
-        // we already set the size in the surface constructor we set for
-        // printing, so just get those values here
-        size = reinterpret_cast<gfxOS2Surface*>(mPrintingSurface.get())->GetSize();
-        // as they are in pixels we need to scale them to app units
-        size.width = NSFloatPixelsToAppUnits(size.width, AppUnitsPerDevPixel());
-        size.height = NSFloatPixelsToAppUnits(size.height, AppUnitsPerDevPixel());
-        // still need to get the depth from the device context
-        HDC dc = GetPrintHDC();
-        LONG value;
-        if (DevQueryCaps(dc, CAPS_COLOR_BITCOUNT, 1, &value))
-            mDepth = value;
-        else
-            mDepth = 8; // default to 8bpp, should be enough for printers
-        break;
-    }
+        {
+            inPoints = PR_FALSE;
+            // we already set the size in the surface constructor we set for
+            // printing, so just get those values here
+            size = reinterpret_cast<gfxOS2Surface*>(mPrintingSurface.get())->GetSize();
+            // as they are in pixels we need to scale them to app units
+            size.width = NSFloatPixelsToAppUnits(size.width, AppUnitsPerDevPixel());
+            size.height = NSFloatPixelsToAppUnits(size.height, AppUnitsPerDevPixel());
+            // still need to get the depth from the device context
+            HDC dc = GpiQueryDevice(reinterpret_cast<gfxOS2Surface*>(mPrintingSurface.get())->GetPS());
+            LONG value;
+            if (DevQueryCaps(dc, CAPS_COLOR_BITCOUNT, 1, &value))
+                mDepth = value;
+            else
+                mDepth = 8; // default to 8bpp, should be enough for printers
+            break;
+        }
 #endif
     default:
         NS_ERROR("trying to print to unknown surface type");
     }
 
     if (inPoints) {
         // For printing, CSS inches and physical inches are identical
         // so it doesn't matter which we use here
         mWidth = NSToCoordRound(float(size.width) * AppUnitsPerPhysicalInch() / 72);
         mHeight = NSToCoordRound(float(size.height) * AppUnitsPerPhysicalInch() / 72);
     } else {
         mWidth = NSToIntRound(size.width);
         mHeight = NSToIntRound(size.height);
     }
 }
 
-PRBool nsThebesDeviceContext::CheckDPIChange() {
+PRBool nsDeviceContext::CheckDPIChange() {
     PRInt32 oldDevPixels = mAppUnitsPerDevNotScaledPixel;
     PRInt32 oldInches = mAppUnitsPerPhysicalInch;
 
     SetDPI();
 
     return oldDevPixels != mAppUnitsPerDevNotScaledPixel ||
-           oldInches != mAppUnitsPerPhysicalInch;
+        oldInches != mAppUnitsPerPhysicalInch;
 }
 
 PRBool
-nsThebesDeviceContext::SetPixelScale(float aScale)
+nsDeviceContext::SetPixelScale(float aScale)
 {
     if (aScale <= 0) {
         NS_NOTREACHED("Invalid pixel scale value");
         return PR_FALSE;
     }
     PRInt32 oldAppUnitsPerDevPixel = mAppUnitsPerDevPixel;
     mPixelScale = aScale;
     UpdateScaledAppUnits();
     return oldAppUnitsPerDevPixel != mAppUnitsPerDevPixel;
 }
 
 void
-nsThebesDeviceContext::UpdateScaledAppUnits()
+nsDeviceContext::UpdateScaledAppUnits()
 {
     mAppUnitsPerDevPixel =
         PR_MAX(1, NSToIntRound(float(mAppUnitsPerDevNotScaledPixel) / mPixelScale));
 }
-
-#if defined(XP_WIN) || defined(XP_OS2)
-HDC
-nsThebesDeviceContext::GetPrintHDC()
-{
-    if (mPrintingSurface) {
-        switch (mPrintingSurface->GetType()) {
-#ifdef XP_WIN
-            case gfxASurface::SurfaceTypeWin32:
-            case gfxASurface::SurfaceTypeWin32Printing:
-                return reinterpret_cast<gfxWindowsSurface*>(mPrintingSurface.get())->GetDC();
-#endif
-
-#ifdef XP_OS2
-            case gfxASurface::SurfaceTypeOS2:
-                return GpiQueryDevice(reinterpret_cast<gfxOS2Surface*>(mPrintingSurface.get())->GetPS());
-#endif
-
-            default:
-                NS_ERROR("invalid surface type in GetPrintHDC");
-                break;
-        }
-    }
-
-    return nsnull;
-}
-#endif
rename from gfx/src/nsThebesDeviceContext.h
rename to gfx/src/nsDeviceContext.h
--- a/gfx/src/nsThebesDeviceContext.h
+++ b/gfx/src/nsDeviceContext.h
@@ -1,9 +1,9 @@
-/* -*- Mode: C++; tab-width: 20; indent-tabs-mode: nil; c-basic-offset: 4 -*- */
+/* -*- Mode: C++; indent-tabs-mode: nil; c-basic-offset: 4 -*- */
 /* ***** BEGIN LICENSE BLOCK *****
  * Version: MPL 1.1/GPL 2.0/LGPL 2.1
  *
  * The contents of this file are subject to the Mozilla Public License Version
  * 1.1 (the "License"); you may not use this file except in compliance with
  * the License. You may obtain a copy of the License at
  * http://www.mozilla.org/MPL/
  *
@@ -32,124 +32,378 @@
  * use your version of this file under the terms of the MPL, indicate your
  * 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 ***** */
 
-#ifndef _NS_THEBESDEVICECONTEXT_H_
-#define _NS_THEBESDEVICECONTEXT_H_
+#ifndef _NS_DEVICECONTEXT_H_
+#define _NS_DEVICECONTEXT_H_
 
-#include "nsIScreenManager.h"
-#include "nsIDeviceContext.h"
-#include "nsIDeviceContextSpec.h"
 #include "nsCOMPtr.h"
 #include "nsIAtom.h"
+#include "nsIDeviceContextSpec.h"
+#include "nsIScreenManager.h"
+#include "nsIWidget.h"
+#include "nsCoord.h"
 #include "gfxContext.h"
 
-#ifdef XP_WIN
-#include "gfxWindowsSurface.h"
-#elif defined(XP_OS2)
-#include "gfxOS2Surface.h"
-#endif
+class nsIView;
+class nsFontCache;
+class gfxUserFontSet;
+
+typedef enum {
+    eSystemFont_Caption,         // css2
+    eSystemFont_Icon,
+    eSystemFont_Menu,
+    eSystemFont_MessageBox,
+    eSystemFont_SmallCaption,
+    eSystemFont_StatusBar,
 
-class nsFontCache;
+    eSystemFont_Window,          // css3
+    eSystemFont_Document,
+    eSystemFont_Workspace,
+    eSystemFont_Desktop,
+    eSystemFont_Info,
+    eSystemFont_Dialog,
+    eSystemFont_Button,
+    eSystemFont_PullDownMenu,
+    eSystemFont_List,
+    eSystemFont_Field,
 
-class nsThebesDeviceContext : public nsIDeviceContext
+    eSystemFont_Tooltips,        // moz
+    eSystemFont_Widget
+} nsSystemFontID;
+
+class nsDeviceContext
 {
 public:
-    nsThebesDeviceContext();
-    virtual ~nsThebesDeviceContext();
+    nsDeviceContext();
+    ~nsDeviceContext();
+
+    NS_INLINE_DECL_REFCOUNTING(nsDeviceContext)
+
+    /**
+     * Initialize the device context from a widget
+     * @param aWidget a widget to initialize the device context from
+     * @return error status
+     */
+    nsresult Init(nsIWidget *aWidget);
 
-    static void Shutdown();
+    /**
+     * Initialize the device context from a device context spec
+     * @param aDevSpec the specification of the printing device
+     * @return error status
+     */
+    nsresult InitForPrinting(nsIDeviceContextSpec *aDevSpec);
 
-    NS_DECL_ISUPPORTS
+    /**
+     * Create a rendering context and initialize it from an nsIView
+     * @param aView view to initialize context from
+     * @param aContext out parameter for new rendering context
+     * @return error status
+     */
+    nsresult CreateRenderingContext(nsIView *aView,
+                                    nsRenderingContext *&aContext);
 
-    NS_IMETHOD Init(nsIWidget *aWidget);
-    NS_IMETHOD InitForPrinting(nsIDeviceContextSpec *aDevSpec);
-    NS_IMETHOD CreateRenderingContext(nsIView *aView, nsRenderingContext *&aContext);
-    NS_IMETHOD CreateRenderingContext(nsIWidget *aWidget, nsRenderingContext *&aContext);
-    NS_IMETHOD CreateRenderingContext(nsRenderingContext *&aContext);
-    NS_IMETHOD CreateRenderingContextInstance(nsRenderingContext *&aContext);
+    /**
+     * Create a rendering context and initialize it from an nsIWidget
+     * @param aWidget widget to initialize context from
+     * @param aContext out parameter for new rendering context
+     * @return error status
+     */
+    nsresult CreateRenderingContext(nsIWidget *aWidget,
+                                    nsRenderingContext *&aContext);
+
+    /**
+     * Create a rendering context and initialize it.
+     * @param aContext out parameter for new rendering context
+     * @return error status
+     */
+    nsresult CreateRenderingContext(nsRenderingContext *&aContext);
+
+    /**
+     * Create an uninitalised rendering context.
+     * @param aContext out parameter for new rendering context
+     * @return error status
+     */
+    nsresult CreateRenderingContextInstance(nsRenderingContext *&aContext);
+
+    /**
+     * We are in the process of creating the native widget for
+     * aWidget.  Do any device-specific processing required to
+     * initialize the native widget for this device. A pointer to some
+     * platform-specific data is returned in aOut.
+     */
+    nsresult PrepareNativeWidget(nsIWidget *aWidget, void **aOut);
+
+    /**
+     * Gets the number of app units in one CSS pixel; this number is global,
+     * not unique to each device context.
+     */
+    static PRInt32 AppUnitsPerCSSPixel() { return 60; }
 
-    NS_IMETHOD GetMetricsFor(const nsFont& aFont, nsIAtom* aLanguage,
-                             gfxUserFontSet* aUserFontSet,
-                             nsFontMetrics*& aMetrics);
-    NS_IMETHOD GetMetricsFor(const nsFont& aFont,
-                             gfxUserFontSet* aUserFontSet,
-                             nsFontMetrics*& aMetrics);
+    /**
+     * Convert app units to CSS pixels.  This is a global scale factor.
+     */
+    static gfxFloat AppUnitsToGfxCSSPixels(nscoord aAppUnits)
+    { return gfxFloat(aAppUnits) / AppUnitsPerCSSPixel(); }
+
+    /**
+     * Gets the number of app units in one device pixel; this number
+     * is usually a factor of AppUnitsPerCSSPixel(), although that is
+     * not guaranteed.
+     */
+    PRInt32 AppUnitsPerDevPixel() const { return mAppUnitsPerDevPixel; }
 
-    NS_IMETHOD FirstExistingFont(const nsFont& aFont, nsString& aFaceName);
+    /**
+     * Convert device pixels which is used for gfx/thebes to nearest
+     * (rounded) app units
+     */
+    nscoord GfxUnitsToAppUnits(gfxFloat aGfxUnits) const
+    { return nscoord(NS_round(aGfxUnits * AppUnitsPerDevPixel())); }
+
+    /**
+     * Convert app units to device pixels which is used for gfx/thebes.
+     */
+    gfxFloat AppUnitsToGfxUnits(nscoord aAppUnits) const
+    { return gfxFloat(aAppUnits) / AppUnitsPerDevPixel(); }
+
+    /**
+     * Gets the number of app units in one physical inch; this is the
+     * device's DPI times AppUnitsPerDevPixel().
+     */
+    PRInt32 AppUnitsPerPhysicalInch() const
+    { return mAppUnitsPerPhysicalInch; }
 
-    NS_IMETHOD GetLocalFontName(const nsString& aFaceName, nsString& aLocalName,
-                                PRBool& aAliased);
+    /**
+     * Gets the number of app units in one CSS inch; this is
+     * 96 times AppUnitsPerCSSPixel.
+     */
+    static PRInt32 AppUnitsPerCSSInch() { return 96 * AppUnitsPerCSSPixel(); }
+
+    /**
+     * Get the unscaled ratio of app units to dev pixels; useful if something
+     * needs to be converted from to unscaled pixels
+     */
+    PRInt32 UnscaledAppUnitsPerDevPixel() const
+    { return mAppUnitsPerDevNotScaledPixel; }
 
-    NS_IMETHOD CreateFontCache();
-    NS_IMETHOD FontMetricsDeleted(const nsFontMetrics* aFontMetrics);
-    NS_IMETHOD FlushFontCache(void);
+    /**
+     * Fill in an nsFont based on the ID of a system font.  This function
+     * may or may not fill in the size, so the size should be set to a
+     * reasonable default before calling.
+     *
+     * @param aID    The system font ID.
+     * @param aInfo  The font structure to be filled in.
+     * @return error status
+     */
+    nsresult GetSystemFont(nsSystemFontID aID, nsFont *aFont) const;
 
-    NS_IMETHOD PrepareNativeWidget(nsIWidget *aWidget, void **aOut);
+    /**
+     * Clear cached system fonts (refresh from theme when requested).
+     */
+    static void ClearCachedSystemFonts();
+
+    /**
+     * Get the nsFontMetrics that describe the properties of
+     * an nsFont.
+     * @param aFont font description to obtain metrics for
+     * @param aLanguage the language of the document
+     * @param aMetrics out parameter for font metrics
+     * @param aUserFontSet user font set
+     * @return error status
+     */
+    nsresult GetMetricsFor(const nsFont& aFont, nsIAtom* aLanguage,
+                           gfxUserFontSet* aUserFontSet,
+                           nsFontMetrics*& aMetrics);
 
-    NS_IMETHOD GetSystemFont(nsSystemFontID aID, nsFont *aFont) const;
-    NS_IMETHOD ClearCachedSystemFonts();
+    /**
+     * Get the nsFontMetrics that describe the properties of
+     * an nsFont.
+     * @param aFont font description to obtain metrics for
+     * @param aMetrics out parameter for font metrics
+     * @param aUserFontSet user font set
+     * @return error status
+     */
+    nsresult GetMetricsFor(const nsFont& aFont,
+                           gfxUserFontSet* aUserFontSet,
+                           nsFontMetrics*& aMetrics);
+
+    /**
+     * Notification when a font metrics instance created for this device is
+     * about to be deleted
+     */
+    nsresult FontMetricsDeleted(const nsFontMetrics* aFontMetrics);
 
-    NS_IMETHOD CheckFontExistence(const nsString& aFaceName);
+    /**
+     * Attempt to free up resources by flushing out any fonts no longer
+     * referenced by anything other than the font cache itself.
+     * @return error status
+     */
+    nsresult FlushFontCache();
 
-    NS_IMETHOD GetDepth(PRUint32& aDepth);
+    /**
+     * Check to see if a particular named font exists.
+     * @param aFontName character string of font face name
+     * @return NS_OK if font is available, else font is unavailable
+     */
+    nsresult CheckFontExistence(const nsString& aFaceName);
+    nsresult FirstExistingFont(const nsFont& aFont, nsString& aFaceName);
+    nsresult GetLocalFontName(const nsString& aFaceName, nsString& aLocalName,
+                              PRBool& aAliased);
+
 
-    NS_IMETHOD GetDeviceSurfaceDimensions(nscoord& aWidth, nscoord& aHeight);
-    NS_IMETHOD GetRect(nsRect& aRect);
-    NS_IMETHOD GetClientRect(nsRect& aRect);
+    /**
+     * Return the bit depth of the device.
+     */
+    nsresult GetDepth(PRUint32& aDepth);
+
+    /**
+     * Get the size of the displayable area of the output device
+     * in app units.
+     * @param aWidth out parameter for width
+     * @param aHeight out parameter for height
+     * @return error status
+     */
+    nsresult GetDeviceSurfaceDimensions(nscoord& aWidth, nscoord& aHeight);
 
-    /* printing goop */
-    NS_IMETHOD PrepareDocument(PRUnichar *aTitle, 
-                               PRUnichar *aPrintToFileName);
+    /**
+     * Get the size of the content area of the output device in app
+     * units.  This corresponds on a screen device, for instance, to
+     * the entire screen.
+     * @param aRect out parameter for full rect. Position (x,y) will
+     *              be (0,0) or relative to the primary monitor if
+     *              this is not the primary.
+     * @return error status
+     */
+    nsresult GetRect(nsRect& aRect);
+
+    /**
+     * Get the size of the content area of the output device in app
+     * units.  This corresponds on a screen device, for instance, to
+     * the area reported by GetDeviceSurfaceDimensions, minus the
+     * taskbar (Windows) or menubar (Macintosh).
+     * @param aRect out parameter for client rect. Position (x,y) will
+     *              be (0,0) adjusted for any upper/left non-client
+     *              space if present or relative to the primary
+     *              monitor if this is not the primary.
+     * @return error status
+     */
+    nsresult GetClientRect(nsRect& aRect);
 
-    NS_IMETHOD BeginDocument(PRUnichar  *aTitle, 
-                             PRUnichar  *aPrintToFileName,
-                             PRInt32     aStartPage, 
-                             PRInt32     aEndPage);
+    /**
+     * Do anything that needs to be done to prepare for printing.
+     * @param aTitle - title of Document
+     * @param aPrintToFileName - name of file to print to, if NULL
+     * then don't print to file
+     *
+     * @return error status
+     */
+    nsresult PrepareDocument(PRUnichar *aTitle,
+                             PRUnichar *aPrintToFileName);
+
+    /**
+     * Inform the output device that output of a document is beginning
+     * Used for print related device contexts. Must be matched 1:1 with
+     * EndDocument() or AbortDocument().
+     *
+     * @param aTitle - title of Document
+     * @param aPrintToFileName - name of file to print to, if NULL
+     * then don't print to file
+     * @param aStartPage - starting page number (must be greater than zero)
+     * @param aEndPage - ending page number (must be less than or
+     * equal to number of pages)
+     *
+     * @return error status
+     */
+    nsresult BeginDocument(PRUnichar  *aTitle,
+                           PRUnichar  *aPrintToFileName,
+                           PRInt32     aStartPage,
+                           PRInt32     aEndPage);
+
+    /**
+     * Inform the output device that output of a document is ending.
+     * Used for print related device contexts. Must be matched 1:1 with
+     * BeginDocument()
+     * @return error status
+     */
+    nsresult EndDocument();
 
-    NS_IMETHOD EndDocument(void);
-    NS_IMETHOD AbortDocument(void);
-    NS_IMETHOD BeginPage(void);
-    NS_IMETHOD EndPage(void);
-    /* end printing goop */
+    /**
+     * Inform the output device that output of a document is being aborted.
+     * Must be matched 1:1 with BeginDocument()
+     * @return error status
+     */
+    nsresult AbortDocument();
 
-    virtual PRBool CheckDPIChange();
+    /**
+     * Inform the output device that output of a page is beginning
+     * Used for print related device contexts. Must be matched 1:1 with
+     * EndPage() and within a BeginDocument()/EndDocument() pair.
+     * @return error status
+     */
+    nsresult BeginPage();
+
+    /**
+     * Inform the output device that output of a page is ending
+     * Used for print related device contexts. Must be matched 1:1 with
+     * BeginPage() and within a BeginDocument()/EndDocument() pair.
+     * @return error status
+     */
+    nsresult EndPage();
 
-    virtual PRBool SetPixelScale(float aScale);
-
-    PRBool IsPrinterSurface(void);
+    /**
+     * Check to see if the DPI has changed
+     * @return whether there was actually a change in the DPI (whether
+     *         AppUnitsPerDevPixel() or AppUnitsPerPhysicalInch()
+     *         changed)
+     */
+    PRBool CheckDPIChange();
 
-#if defined(XP_WIN) || defined(XP_OS2)
-    HDC GetPrintHDC();
-#endif
+    /**
+     * Set the pixel scaling factor: all lengths are multiplied by this factor
+     * when we convert them to device pixels. Returns whether the ratio of
+     * app units to dev pixels changed because of the scale factor.
+     */
+    PRBool SetPixelScale(float aScale);
+
+    /**
+     * Get the pixel scaling factor; defaults to 1.0, but can be changed with
+     * SetPixelScale.
+     */
+    float GetPixelScale() const { return mPixelScale; }
+
+    /**
+     * True if this device context was created for printing.
+     */
+    PRBool IsPrinterSurface();
 
 protected:
-    void GetLocaleLanguage(void);
-    nsresult SetDPI();
+    void CreateFontCache();
+    void GetLocaleLanguage();
+    void SetDPI();
     void ComputeClientRectUsingScreen(nsRect *outRect);
     void ComputeFullAreaUsingScreen(nsRect *outRect);
     void FindScreen(nsIScreen **outScreen);
     void CalcPrintingSize();
     void UpdateScaledAppUnits();
 
-    PRUint32          mDepth;
-    nsFontCache*      mFontCache;
-    nsCOMPtr<nsIAtom> mLocaleLanguage; // XXX temp fix for performance bug
-    nsCOMPtr<nsIWidget> mWidget;
+    nscoord  mWidth;
+    nscoord  mHeight;
+    PRUint32 mDepth;
+    PRInt32  mAppUnitsPerDevPixel;
+    PRInt32  mAppUnitsPerDevNotScaledPixel;
+    PRInt32  mAppUnitsPerPhysicalInch;
+    float    mPixelScale;
+    float    mPrintingScale;
 
-private:
-    nsCOMPtr<nsIScreenManager> mScreenManager;
-
-    nscoord mWidth;
-    nscoord mHeight;
-
-    nsRefPtr<gfxASurface> mPrintingSurface;
-    float mPrintingScale;
+    nsFontCache*                   mFontCache;
+    nsCOMPtr<nsIAtom>              mLocaleLanguage;
+    nsCOMPtr<nsIWidget>            mWidget;
+    nsCOMPtr<nsIScreenManager>     mScreenManager;
     nsCOMPtr<nsIDeviceContextSpec> mDeviceContextSpec;
+    nsRefPtr<gfxASurface>          mPrintingSurface;
 };
 
-#endif /* _NS_CAIRODEVICECONTEXT_H_ */
-
+#endif /* _NS_DEVICECONTEXT_H_ */
--- a/gfx/src/nsFontMetrics.cpp
+++ b/gfx/src/nsFontMetrics.cpp
@@ -34,17 +34,17 @@
  * 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 "nsFontMetrics.h"
 #include "nsBoundingMetrics.h"
 #include "nsRenderingContext.h"
-#include "nsThebesDeviceContext.h"
+#include "nsDeviceContext.h"
 #include "gfxTextRunCache.h"
 
 namespace {
 
 class AutoTextRun : public gfxTextRunCache::AutoTextRun {
 public:
     AutoTextRun(nsFontMetrics* aMetrics, nsRenderingContext* aRC,
                 const char* aString, PRInt32 aLength)
@@ -100,24 +100,24 @@ nsFontMetrics::nsFontMetrics()
 nsFontMetrics::~nsFontMetrics()
 {
     if (mDeviceContext)
         mDeviceContext->FontMetricsDeleted(this);
 }
 
 nsresult
 nsFontMetrics::Init(const nsFont& aFont, nsIAtom* aLanguage,
-                    nsIDeviceContext *aContext,
+                    nsDeviceContext *aContext,
                     gfxUserFontSet *aUserFontSet)
 {
     NS_ABORT_IF_FALSE(mP2A == -1, "already initialized");
 
     mFont = aFont;
     mLanguage = aLanguage;
-    mDeviceContext = (nsThebesDeviceContext*)aContext;
+    mDeviceContext = aContext;
     mP2A = mDeviceContext->AppUnitsPerDevPixel();
 
     gfxFontStyle style(aFont.style,
                        aFont.weight,
                        aFont.stretch,
                        gfxFloat(aFont.size) / mP2A,
                        aLanguage,
                        aFont.sizeAdjust,
--- a/gfx/src/nsFontMetrics.h
+++ b/gfx/src/nsFontMetrics.h
@@ -40,19 +40,18 @@
 #define NSFONTMETRICS__H__
 
 #include "nsCOMPtr.h"
 #include "nsCoord.h"
 #include "nsFont.h"
 #include "gfxFont.h"
 
 class nsIAtom;
-class nsIDeviceContext;
+class nsDeviceContext;
 class nsRenderingContext;
-class nsThebesDeviceContext;
 struct nsBoundingMetrics;
 
 /**
  * Font metrics
  *
  * This class may be somewhat misnamed. A better name might be
  * nsFontList. The style system uses the nsFont struct for various
  * font properties, one of which is font-family, which can contain a
@@ -75,20 +74,20 @@ public:
     ~nsFontMetrics();
 
     NS_INLINE_DECL_REFCOUNTING(nsFontMetrics)
 
     /**
      * Initialize the font metrics. Call this after creating the font metrics.
      * Font metrics you get from the font cache do NOT need to be initialized
      *
-     * @see nsIDeviceContext#GetMetricsFor()
+     * @see nsDeviceContext#GetMetricsFor()
      */
     nsresult Init(const nsFont& aFont, nsIAtom* aLanguage,
-                  nsIDeviceContext *aContext,
+                  nsDeviceContext *aContext,
                   gfxUserFontSet *aUserFontSet = nsnull);
 
     /**
      * Destroy this font metrics. This breaks the association between
      * the font metrics and the device context.
      */
     void Destroy();
 
@@ -233,14 +232,14 @@ public:
     PRInt32 AppUnitsPerDevPixel() { return mP2A; }
 
 protected:
     const gfxFont::Metrics& GetMetrics() const;
 
     nsFont mFont;
     nsRefPtr<gfxFontGroup> mFontGroup;
     nsCOMPtr<nsIAtom> mLanguage;
-    nsThebesDeviceContext *mDeviceContext;
+    nsDeviceContext *mDeviceContext;
     PRInt32 mP2A;
     PRPackedBool mTextRunRTL;
 };
 
 #endif /* NSFONTMETRICS__H__ */
--- a/gfx/src/nsGfxCIID.h
+++ b/gfx/src/nsGfxCIID.h
@@ -33,20 +33,16 @@
  * 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 ***** */
 
 #ifndef nsGfxCIID_h__
 #define nsGfxCIID_h__
 
-#define NS_DEVICE_CONTEXT_CID \
-{ 0x6049b262, 0xc1e6, 0x11d1, \
-{ 0xa8, 0x27, 0x00, 0x40, 0x95, 0x9a, 0x28, 0xc9 } }
-
 #define NS_FONT_ENUMERATOR_CID \
 { 0xa6cf9115, 0x15b3, 0x11d2, \
 { 0x93, 0x2e, 0x00, 0x80, 0x5f, 0x8a, 0xdd, 0x32 } }
 
 #define NS_REGION_CID \
 { 0xe12752f0, 0xee9a, 0x11d1, \
 { 0xa8, 0x2a, 0x00, 0x40, 0x95, 0x9a, 0x28, 0xc9 } }
 
deleted file mode 100644
--- a/gfx/src/nsIDeviceContext.h
+++ /dev/null
@@ -1,386 +0,0 @@
-/* -*- Mode: C++; tab-width: 2; indent-tabs-mode: nil; c-basic-offset: 2 -*- */
-/* ***** BEGIN LICENSE BLOCK *****
- * Version: MPL 1.1/GPL 2.0/LGPL 2.1
- *
- * The contents of this file are subject to the Mozilla Public License Version
- * 1.1 (the "License"); you may not use this file except in compliance with
- * the License. You may obtain a copy of the License at
- * http://www.mozilla.org/MPL/
- *
- * Software distributed under the License is distributed on an "AS IS" basis,
- * WITHOUT WARRANTY OF ANY KIND, either express or implied. See the License
- * for the specific language governing rights and limitations under the
- * License.
- *
- * The Original Code is mozilla.org code.
- *
- * The Initial Developer of the Original Code is
- * Netscape Communications Corporation.
- * Portions created by the Initial Developer are Copyright (C) 1998
- * the Initial Developer. All Rights Reserved.
- *
- * Contributor(s):
- *   Roland Mainz <roland.mainz@informatik.med.uni-giessen.de>
- *
- * Alternatively, the contents of this file may be used under the terms of
- * either of the GNU General Public License Version 2 or later (the "GPL"),
- * or the GNU Lesser General Public License Version 2.1 or later (the "LGPL"),
- * in which case the provisions of the GPL or the LGPL are applicable instead
- * of those above. If you wish to allow use of your version of this file only
- * under the terms of either the GPL or the LGPL, and not to allow others to
- * use your version of this file under the terms of the MPL, indicate your
- * 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 ***** */
-
-#ifndef nsIDeviceContext_h___
-#define nsIDeviceContext_h___
-
-#include "nsISupports.h"
-#include "nsCoord.h"
-#include "gfxTypes.h"
-#include "nsStringFwd.h"
-
-class nsIView;
-class nsFontMetrics;
-class nsIWidget;
-class nsIDeviceContextSpec;
-class nsIAtom;
-class nsRect;
-class gfxUserFontSet;
-class nsRenderingContext;
-struct nsFont;
-
-#define NS_IDEVICE_CONTEXT_IID   \
-{ 0x30a9d22f, 0x8e51, 0x40af, \
-  { 0xa1, 0xf5, 0x48, 0xe3, 0x00, 0xaa, 0xa9, 0x27 } }
-
-  typedef enum {
-    eSystemFont_Caption,         // css2
-    eSystemFont_Icon,
-    eSystemFont_Menu,
-    eSystemFont_MessageBox,
-    eSystemFont_SmallCaption,
-    eSystemFont_StatusBar,
-
-    eSystemFont_Window,          // css3
-    eSystemFont_Document,
-    eSystemFont_Workspace,
-    eSystemFont_Desktop,
-    eSystemFont_Info,
-    eSystemFont_Dialog,
-    eSystemFont_Button,
-    eSystemFont_PullDownMenu,
-    eSystemFont_List,
-    eSystemFont_Field,
-
-    eSystemFont_Tooltips,        // moz
-    eSystemFont_Widget
-  } nsSystemFontID;
-
-class nsIDeviceContext : public nsISupports
-{
-public:
-  NS_DECLARE_STATIC_IID_ACCESSOR(NS_IDEVICE_CONTEXT_IID)
-
-  /**
-   * Initialize the device context from a widget
-   * @param aWidget a widget to initialize the device context from
-   * @return error status
-   */
-  NS_IMETHOD  Init(nsIWidget* aWidget) = 0;
-
-  /**
-   * Initialize the device context from a device context spec
-   * @param aDevSpec the specification of the printng device (platform-specific)
-   * @return error status
-   */
-  NS_IMETHOD  InitForPrinting(nsIDeviceContextSpec* aDevSpec) = 0;
-
-  /**
-   * Create a rendering context and initialize it from an nsIView
-   * @param aView view to initialize context from
-   * @param aContext out parameter for new rendering context
-   * @return error status
-   */
-  NS_IMETHOD  CreateRenderingContext(nsIView *aView, nsRenderingContext *&aContext) = 0;
-
-  /**
-   * Create a rendering context and initialize it from an nsIWidget
-   * @param aWidget widget to initialize context from
-   * @param aContext out parameter for new rendering context
-   * @return error status
-   */
-  NS_IMETHOD  CreateRenderingContext(nsIWidget *aWidget, nsRenderingContext *&aContext) = 0;
-
-  /**
-   * Create a rendering context and initialize it.
-   * @param aContext out parameter for new rendering context
-   * @return error status
-   */
-  NS_IMETHOD  CreateRenderingContext(nsRenderingContext *&aContext) = 0;
-
-  /**
-   * Create an uninitalised rendering context.
-   * @param aContext out parameter for new rendering context
-   * @return error status
-   */
-  NS_IMETHOD  CreateRenderingContextInstance(nsRenderingContext *&aContext) = 0;
-
-  /**
-   * We are in the process of creating the native widget for aWidget.
-   * Do any device-specific processing required to initialize the
-   * native widget for this device. A pointer to some platform-specific data is
-   * returned in aOut.
-   *
-   * GTK2 calls this to get the required visual for the window.
-   */
-  NS_IMETHOD PrepareNativeWidget(nsIWidget* aWidget, void** aOut) = 0;
-
-  /**
-   * Gets the number of app units in one CSS pixel; this number is global,
-   * not unique to each device context.
-   */
-  static PRInt32 AppUnitsPerCSSPixel() { return 60; }
-
-  /**
-   * Convert app units to CSS pixels which is used in gfx/thebes.
-   */
-  static gfxFloat AppUnitsToGfxCSSPixels(nscoord aAppUnits)
-  { return gfxFloat(aAppUnits) / AppUnitsPerCSSPixel(); }
-
-  /**
-   * Gets the number of app units in one device pixel; this number is usually
-   * a factor of AppUnitsPerCSSPixel(), although that is not guaranteed.
-   */
-  PRInt32 AppUnitsPerDevPixel() const { return mAppUnitsPerDevPixel; }
-
-  /**
-   * Convert device pixels which is used for gfx/thebes to nearest (rounded)
-   * app units
-   */
-  nscoord GfxUnitsToAppUnits(gfxFloat aGfxUnits) const
-  { return nscoord(NS_round(aGfxUnits * AppUnitsPerDevPixel())); }
-
-  /**
-   * Convert app units to device pixels which is used for gfx/thebes.
-   */
-  gfxFloat AppUnitsToGfxUnits(nscoord aAppUnits) const
-  { return gfxFloat(aAppUnits) / AppUnitsPerDevPixel(); }
-
-  /**
-   * Gets the number of app units in one physical inch; this is the
-   * device's DPI times AppUnitsPerDevPixel().
-   */
-  PRInt32 AppUnitsPerPhysicalInch() const { return mAppUnitsPerPhysicalInch; }
-
-  /**
-   * Gets the number of app units in one CSS inch; this is the
-   * 96 times AppUnitsPerCSSPixel.
-   */
-  static PRInt32 AppUnitsPerCSSInch() { return 96 * AppUnitsPerCSSPixel(); }
-
-  /**
-   * Fill in an nsFont based on the ID of a system font.  This function
-   * may or may not fill in the size, so the size should be set to a
-   * reasonable default before calling.
-   *
-   * @param aID    The system font ID.
-   * @param aInfo  The font structure to be filled in.
-   * @return error status
-   */
-  NS_IMETHOD  GetSystemFont(nsSystemFontID aID, nsFont *aFont) const = 0;
-
-  /**
-   * Get the nsFontMetrics that describe the properties of
-   * an nsFont.
-   * @param aFont font description to obtain metrics for
-   * @param aLanguage the language of the document
-   * @param aMetrics out parameter for font metrics
-   * @param aUserFontSet user font set
-   * @return error status
-   */
-  NS_IMETHOD  GetMetricsFor(const nsFont& aFont, nsIAtom* aLanguage,
-                            gfxUserFontSet* aUserFontSet,
-                            nsFontMetrics*& aMetrics) = 0;
-
-  /**
-   * Get the nsFontMetrics that describe the properties of
-   * an nsFont.
-   * @param aFont font description to obtain metrics for
-   * @param aMetrics out parameter for font metrics
-   * @param aUserFontSet user font set
-   * @return error status
-   */
-  NS_IMETHOD  GetMetricsFor(const nsFont& aFont, gfxUserFontSet* aUserFontSet,
-                            nsFontMetrics*& aMetrics) = 0;
-
-  /**
-   * Check to see if a particular named font exists.
-   * @param aFontName character string of font face name
-   * @return NS_OK if font is available, else font is unavailable
-   */
-  NS_IMETHOD CheckFontExistence(const nsString& aFaceName) = 0;
-  NS_IMETHOD FirstExistingFont(const nsFont& aFont, nsString& aFaceName) = 0;
-
-  NS_IMETHOD GetLocalFontName(const nsString& aFaceName, nsString& aLocalName,
-                              PRBool& aAliased) = 0;
-
-  /**
-   * Notification when a font metrics instance created for this device is
-   * about to be deleted
-   */
-  NS_IMETHOD FontMetricsDeleted(const nsFontMetrics* aFontMetrics) = 0;
-
-  /**
-   * Attempt to free up resoruces by flushing out any fonts no longer
-   * referenced by anything other than the font cache itself.
-   * @return error status
-   */
-  NS_IMETHOD FlushFontCache(void) = 0;
-
-  /**
-   * Return the bit depth of the device.
-   */
-  NS_IMETHOD GetDepth(PRUint32& aDepth) = 0;
-
-  /**
-   * Get the size of the displayable area of the output device
-   * in app units.
-   * @param aWidth out parameter for width
-   * @param aHeight out parameter for height
-   * @return error status
-   */
-  NS_IMETHOD GetDeviceSurfaceDimensions(nscoord &aWidth, nscoord &aHeight) = 0;
-
-  /**
-   * Get the size of the content area of the output device in app units.
-   * This corresponds on a screen device, for instance, to the entire screen.
-   * @param aRect out parameter for full rect. Position (x,y) will be (0,0) or
-   *              relative to the primary monitor if this is not the primary.
-   * @return error status
-   */
-  NS_IMETHOD GetRect ( nsRect &aRect ) = 0;
-
-  /**
-   * Get the size of the content area of the output device in app units.
-   * This corresponds on a screen device, for instance, to the area reported
-   * by GetDeviceSurfaceDimensions, minus the taskbar (Windows) or menubar
-   * (Macintosh).
-   * @param aRect out parameter for client rect. Position (x,y) will be (0,0)
-   *              adjusted for any upper/left non-client space if present or
-   *              relative to the primary monitor if this is not the primary.
-   * @return error status
-   */
-  NS_IMETHOD GetClientRect(nsRect &aRect) = 0;
-
-  /**
-   * This is enables the DeviceContext to anything it needs to do for Printing
-   * before Reflow and BeginDocument is where work can be done after reflow.
-   * @param aTitle - itle of Document
-   * @param aPrintToFileName - name of file to print to, if NULL then don't print to file
-   *
-   * @return error status
-   */
-  NS_IMETHOD PrepareDocument(PRUnichar * aTitle, 
-                             PRUnichar*  aPrintToFileName) = 0;
-
-  //XXX need to work out re-entrancy issues for these APIs... MMP
-  /**
-   * Inform the output device that output of a document is beginning
-   * Used for print related device contexts. Must be matched 1:1 with
-   * EndDocument().
-   * XXX needs to take parameters so that feedback can be given to the
-   * app regarding pagination progress and aborting print operations?
-   *
-   * @param aTitle - itle of Document
-   * @param aPrintToFileName - name of file to print to, if NULL then don't print to file
-   * @param aStartPage - starting page number (must be greater than zero)
-   * @param aEndPage - ending page number     (must be less than or equal to number of pages)
-   *
-   * @return error status
-   */
-  NS_IMETHOD BeginDocument(PRUnichar*  aTitle, 
-                           PRUnichar*  aPrintToFileName,
-                           PRInt32     aStartPage, 
-                           PRInt32     aEndPage) = 0;
-
-  /**
-   * Inform the output device that output of a document is ending.
-   * Used for print related device contexts. Must be matched 1:1 with
-   * BeginDocument()
-   * @return error status
-   */
-  NS_IMETHOD EndDocument(void) = 0;
-
-  /**
-   * Inform the output device that output of a document is being aborted.
-   * Must be matched 1:1 with BeginDocument()
-   * @return error status
-   */
-  NS_IMETHOD AbortDocument(void) = 0;
-
-  /**
-   * Inform the output device that output of a page is beginning
-   * Used for print related device contexts. Must be matched 1:1 with
-   * EndPage() and within a BeginDocument()/EndDocument() pair.
-   * @return error status
-   */
-  NS_IMETHOD BeginPage(void) = 0;
-
-  /**
-   * Inform the output device that output of a page is ending
-   * Used for print related device contexts. Must be matched 1:1 with
-   * BeginPage() and within a BeginDocument()/EndDocument() pair.
-   * @return error status
-   */
-  NS_IMETHOD EndPage(void) = 0;
-
-  /**
-   * Clear cached system fonts (refresh from theme when
-   * requested).  This method is effectively static,
-   * and can be called on a new DeviceContext instance
-   * without any initialization.  Only really used by
-   * Gtk native theme stuff.
-   */
-  NS_IMETHOD ClearCachedSystemFonts() = 0;
-
-  /**
-   * Check to see if the DPI has changed
-   * @return whether there was actually a change in the DPI
-   *         (whether AppUnitsPerDevPixel() or AppUnitsPerPhysicalInch() changed)
-  */
-  virtual PRBool CheckDPIChange() = 0;
-
-  /**
-   * Set the pixel scaling factor: all lengths are multiplied by this factor
-   * when we convert them to device pixels. Returns whether the ratio of 
-   * app units to dev pixels changed because of the scale factor.
-   */
-  virtual PRBool SetPixelScale(float aScale) = 0;
-
-  /**
-   * Get the pixel scaling factor; defaults to 1.0, but can be changed with
-   * SetPixelScale.
-   */
-  float GetPixelScale() const { return mPixelScale; }
-
-  /**
-   * Get the unscaled ratio of app units to dev pixels; useful if something
-   * needs to be converted from to unscaled pixels
-   */
-  PRInt32 UnscaledAppUnitsPerDevPixel() const { return mAppUnitsPerDevNotScaledPixel; }
-
-protected:
-  PRInt32 mAppUnitsPerDevPixel;
-  PRInt32 mAppUnitsPerPhysicalInch;
-  PRInt32 mAppUnitsPerDevNotScaledPixel;
-  float  mPixelScale;
-};
-
-NS_DEFINE_STATIC_IID_ACCESSOR(nsIDeviceContext, NS_IDEVICE_CONTEXT_IID)
-
-#endif /* nsIDeviceContext_h___ */
--- a/gfx/src/nsITheme.h
+++ b/gfx/src/nsITheme.h
@@ -47,17 +47,17 @@
 
 struct nsRect;
 struct nsIntRect;
 struct nsIntSize;
 struct nsFont;
 struct nsIntMargin;
 class nsPresContext;
 class nsRenderingContext;
-class nsIDeviceContext;
+class nsDeviceContext;
 class nsIFrame;
 class nsIContent;
 class nsIAtom;
 class nsIWidget;
 
 // IID for the nsITheme interface
 // {887e8902-db6b-41b4-8481-a80f49c5a93a}
  #define NS_ITHEME_IID     \
@@ -106,44 +106,44 @@ public:
    */
   virtual void RegisterWidgetGeometry(nsIWidget* aWindow,
                                       PRUint8 aWidgetType,
                                       const nsIntRect& aRect) {}
 
   /**
    * Get the computed CSS border for the widget, in pixels.
    */
-  NS_IMETHOD GetWidgetBorder(nsIDeviceContext* aContext, 
+  NS_IMETHOD GetWidgetBorder(nsDeviceContext* aContext, 
                              nsIFrame* aFrame,
                              PRUint8 aWidgetType,
                              nsIntMargin* aResult)=0;
 
   /**
    * This method can return PR_FALSE to indicate that the CSS padding
    * value should be used.  Otherwise, it will fill in aResult with the
    * computed padding, in pixels, and return PR_TRUE.
    *
    * XXXldb This ought to be required to return true for non-containers
    * so that we don't let specified padding that has no effect change
    * the computed padding and potentially the size.
    */
-  virtual PRBool GetWidgetPadding(nsIDeviceContext* aContext,
+  virtual PRBool GetWidgetPadding(nsDeviceContext* aContext,
                                   nsIFrame* aFrame,
                                   PRUint8 aWidgetType,
                                   nsIntMargin* aResult) = 0;
 
   /**
    * On entry, *aResult is positioned at 0,0 and sized to the new size
    * of aFrame (aFrame->GetSize() may be stale and should not be used).
    * This method can return PR_FALSE to indicate that no special
    * overflow area is required by the native widget. Otherwise it will
    * fill in aResult with the desired overflow area, in appunits, relative
    * to the frame origin, and return PR_TRUE.
    */
-  virtual PRBool GetWidgetOverflow(nsIDeviceContext* aContext,
+  virtual PRBool GetWidgetOverflow(nsDeviceContext* aContext,
                                    nsIFrame* aFrame,
                                    PRUint8 aWidgetType,
                                    /*INOUT*/ nsRect* aOverflowRect)
   { return PR_FALSE; }
 
   /**
    * Get the minimum border-box size of a widget, in *pixels* (in
    * |aResult|).  If |aIsOverridable| is set to true, this size is a
--- a/gfx/src/nsRect.cpp
+++ b/gfx/src/nsRect.cpp
@@ -32,17 +32,17 @@
  * 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 "nsRect.h"
 #include "nsString.h"
-#include "nsIDeviceContext.h"
+#include "nsDeviceContext.h"
 #include "prlog.h"
 #include <limits.h>
 
 // the mozilla::css::Side sequence must match the nsMargin nscoord sequence
 PR_STATIC_ASSERT((NS_SIDE_TOP == 0) && (NS_SIDE_RIGHT == 1) && (NS_SIDE_BOTTOM == 2) && (NS_SIDE_LEFT == 3));
 
 /* static */
 const nsIntRect nsIntRect::kMaxSizedIntRect(0, 0, INT_MAX, INT_MAX);
@@ -80,24 +80,24 @@ nsRect& nsRect::ExtendForScaling(float a
 
 FILE* operator<<(FILE* out, const nsRect& rect)
 {
   nsAutoString tmp;
 
   // Output the coordinates in fractional pixels so they're easier to read
   tmp.AppendLiteral("{");
   tmp.AppendFloat(NSAppUnitsToFloatPixels(rect.x,
-                       nsIDeviceContext::AppUnitsPerCSSPixel()));
+                       nsDeviceContext::AppUnitsPerCSSPixel()));
   tmp.AppendLiteral(", ");
   tmp.AppendFloat(NSAppUnitsToFloatPixels(rect.y,
-                       nsIDeviceContext::AppUnitsPerCSSPixel()));
+                       nsDeviceContext::AppUnitsPerCSSPixel()));
   tmp.AppendLiteral(", ");
   tmp.AppendFloat(NSAppUnitsToFloatPixels(rect.width,
-                       nsIDeviceContext::AppUnitsPerCSSPixel()));
+                       nsDeviceContext::AppUnitsPerCSSPixel()));
   tmp.AppendLiteral(", ");
   tmp.AppendFloat(NSAppUnitsToFloatPixels(rect.height,
-                       nsIDeviceContext::AppUnitsPerCSSPixel()));
+                       nsDeviceContext::AppUnitsPerCSSPixel()));
   tmp.AppendLiteral("}");
   fputs(NS_LossyConvertUTF16toASCII(tmp).get(), out);
   return out;
 }
 
 #endif // DEBUG
--- a/gfx/src/nsRenderingContext.cpp
+++ b/gfx/src/nsRenderingContext.cpp
@@ -80,24 +80,24 @@ static PRInt32 FindSafeLength(const char
     // Since it's ASCII, we don't need to worry about clusters or RTL
     return PR_MIN(aLength, aMaxChunkLength);
 }
 
 //////////////////////////////////////////////////////////////////////
 //// nsRenderingContext
 
 void
-nsRenderingContext::Init(nsIDeviceContext* aContext,
+nsRenderingContext::Init(nsDeviceContext* aContext,
                          gfxASurface *aThebesSurface)
 {
     Init(aContext, new gfxContext(aThebesSurface));
 }
 
 void
-nsRenderingContext::Init(nsIDeviceContext* aContext,
+nsRenderingContext::Init(nsDeviceContext* aContext,
                          gfxContext *aThebesContext)
 {
     mDeviceContext = aContext;
     mThebes = aThebesContext;
 
     mThebes->SetLineWidth(1.0);
     mP2A = mDeviceContext->AppUnitsPerDevPixel();
 }
--- a/gfx/src/nsRenderingContext.h
+++ b/gfx/src/nsRenderingContext.h
@@ -35,18 +35,17 @@
  * the terms of any one of the MPL, the GPL or the LGPL.
  *
  * ***** END LICENSE BLOCK ***** */
 
 #ifndef NSRENDERINGCONTEXT__H__
 #define NSRENDERINGCONTEXT__H__
 
 #include "nsAutoPtr.h"
-#include "nsCOMPtr.h"
-#include "nsIDeviceContext.h"
+#include "nsDeviceContext.h"
 #include "nsFontMetrics.h"
 #include "nsColor.h"
 #include "nsCoord.h"
 #include "gfxContext.h"
 
 struct nsPoint;
 class nsIntRegion;
 
@@ -60,22 +59,22 @@ typedef enum {
 class nsRenderingContext
 {
 public:
     nsRenderingContext() : mP2A(0.) {}
     // ~nsRenderingContext() {}
 
     NS_INLINE_DECL_REFCOUNTING(nsRenderingContext)
 
-    void Init(nsIDeviceContext* aContext, gfxASurface* aThebesSurface);
-    void Init(nsIDeviceContext* aContext, gfxContext* aThebesContext);
+    void Init(nsDeviceContext* aContext, gfxASurface* aThebesSurface);
+    void Init(nsDeviceContext* aContext, gfxContext* aThebesContext);
 
     // These accessors will never return null.
     gfxContext *ThebesContext() { return mThebes; }
-    nsIDeviceContext *DeviceContext() { return mDeviceContext; }
+    nsDeviceContext *DeviceContext() { return mDeviceContext; }
     PRInt32 AppUnitsPerDevPixel() { return mP2A; }
 
     // Graphics state
 
     void PushState(void);
     void PopState(void);
     void IntersectClip(const nsRect& aRect);
     void SetClip(const nsIntRegion& aRegion);
@@ -143,15 +142,15 @@ public:
                     nscoord aX, nscoord aY);
     void DrawString(const PRUnichar *aString, PRUint32 aLength,
                     nscoord aX, nscoord aY);
 
 protected:
     PRInt32 GetMaxChunkLength();
 
     nsRefPtr<gfxContext> mThebes;
-    nsCOMPtr<nsIDeviceContext> mDeviceContext;
+    nsRefPtr<nsDeviceContext> mDeviceContext;
     nsRefPtr<nsFontMetrics> mFontMetrics;
 
     double mP2A; // cached app units per device pixel value
 };
 
 #endif  // NSRENDERINGCONTEXT__H__
--- a/gfx/src/nsSystemFontsAndroid.h
+++ b/gfx/src/nsSystemFontsAndroid.h
@@ -34,17 +34,17 @@
  * the terms of any one of the MPL, the GPL or the LGPL.
  *
  * ***** END LICENSE BLOCK ***** */
 
 #ifndef _NS_SYSTEMFONTSANDROID_H_
 #define _NS_SYSTEMFONTSANDROID_H_
 
 #include "gfxFont.h"
-#include "nsIDeviceContext.h"
+#include "nsDeviceContext.h"
 
 class nsSystemFontsAndroid
 {
 public:
     nsSystemFontsAndroid();
     ~nsSystemFontsAndroid();
 
     nsresult GetSystemFont(nsSystemFontID anID, nsString *aFontName,
--- a/gfx/src/nsSystemFontsGTK2.h
+++ b/gfx/src/nsSystemFontsGTK2.h
@@ -35,17 +35,17 @@
  * the terms of any one of the MPL, the GPL or the LGPL.
  *
  * ***** END LICENSE BLOCK ***** */
 
 #ifndef _NS_SYSTEMFONTSGTK2_H_
 #define _NS_SYSTEMFONTSGTK2_H_
 
 #include "gfxFont.h"
-#include "nsIDeviceContext.h"
+#include "nsDeviceContext.h"
 
 typedef struct _GtkWidget GtkWidget;
 
 class nsSystemFontsGTK2
 {
 public:
     nsSystemFontsGTK2();
     ~nsSystemFontsGTK2();
--- a/gfx/src/nsSystemFontsMac.h
+++ b/gfx/src/nsSystemFontsMac.h
@@ -34,17 +34,17 @@
  * the terms of any one of the MPL, the GPL or the LGPL.
  *
  * ***** END LICENSE BLOCK ***** */
 
 #ifndef _NS_SYSTEMFONTSMAC_H_
 #define _NS_SYSTEMFONTSMAC_H_
 
 #include "gfxFont.h"
-#include "nsIDeviceContext.h"
+#include "nsDeviceContext.h"
 
 class nsSystemFontsMac
 {
 public:
     nsSystemFontsMac();
     nsresult GetSystemFont(nsSystemFontID anID, nsString *aFontName,
                            gfxFontStyle *aFontStyle) const;
 };
--- a/gfx/src/nsSystemFontsOS2.h
+++ b/gfx/src/nsSystemFontsOS2.h
@@ -37,17 +37,17 @@
  * the terms of any one of the MPL, the GPL or the LGPL.
  *
  * ***** END LICENSE BLOCK ***** */
 
 #ifndef _NS_SYSTEMFONTSOS2_H_
 #define _NS_SYSTEMFONTSOS2_H_
 
 #include "gfxFont.h"
-#include "nsIDeviceContext.h"
+#include "nsDeviceContext.h"
 
 class nsSystemFontsOS2
 {
 public:
     nsSystemFontsOS2();
     nsresult GetSystemFont(nsSystemFontID aID, nsString* aFontName,
                            gfxFontStyle *aFontStyle) const;
 };
--- a/gfx/src/nsSystemFontsQt.h
+++ b/gfx/src/nsSystemFontsQt.h
@@ -35,17 +35,17 @@
  * the terms of any one of the MPL, the GPL or the LGPL.
  *
  * ***** END LICENSE BLOCK ***** */
 
 #ifndef _NS_SYSTEMFONTSQT_H_
 #define _NS_SYSTEMFONTSQT_H_
 
 #include "gfxFont.h"
-#include "nsIDeviceContext.h"
+#include "nsDeviceContext.h"
 
 class nsSystemFontsQt
 {
 public:
     nsSystemFontsQt();
     ~nsSystemFontsQt();
 
     nsresult GetSystemFont(nsSystemFontID anID, nsString *aFontName,
--- a/gfx/src/nsSystemFontsWin.h
+++ b/gfx/src/nsSystemFontsWin.h
@@ -35,17 +35,17 @@
  * the terms of any one of the MPL, the GPL or the LGPL.
  *
  * ***** END LICENSE BLOCK ***** */
 
 #ifndef _NS_SYSTEMFONTSWIN_H_
 #define _NS_SYSTEMFONTSWIN_H_
 
 #include "gfxFont.h"
-#include "nsIDeviceContext.h"
+#include "nsDeviceContext.h"
 #include <windows.h> // need HDC and LOGFONTW
 
 class nsSystemFontsWin
 {
 public:
     nsSystemFontsWin();
 
     nsresult GetSystemFont(nsSystemFontID anID, nsString *aFontName,
--- a/gfx/src/nsThebesGfxFactory.cpp
+++ b/gfx/src/nsThebesGfxFactory.cpp
@@ -35,21 +35,21 @@
  * the terms of any one of the MPL, the GPL or the LGPL.
  *
  * ***** END LICENSE BLOCK ***** */
 
 #include "mozilla/ModuleUtils.h"
 #include "nsCOMPtr.h"
 #include "nsGfxCIID.h"
 
+#include "nsThebesFontEnumerator.h"
+#include "nsThebesRegion.h"
 #include "nsScriptableRegion.h"
 
-#include "nsThebesDeviceContext.h"
-#include "nsThebesRegion.h"
-#include "nsThebesFontEnumerator.h"
+#include "nsDeviceContext.h"
 #include "gfxPlatform.h"
 
 // This service doesn't do anything; its only purpose is to force the
 // gfx module constructor to be called (and hence gfxPlatform::Init).
 // It's invoked at app-startup time and may also be invoked directly
 // (as do_GetService("@mozilla.org/gfx/init;1")) from code (like the
 // libpr0n module constructor) that wants to make sure gfx is
 // initialized.
@@ -57,20 +57,18 @@
 namespace {
 class GfxInitialization : public nsISupports {
     NS_DECL_ISUPPORTS
 };
 
 NS_IMPL_ISUPPORTS0(GfxInitialization)
 }
 
-NS_GENERIC_FACTORY_CONSTRUCTOR(nsThebesDeviceContext)
+NS_GENERIC_FACTORY_CONSTRUCTOR(nsThebesFontEnumerator)
 NS_GENERIC_FACTORY_CONSTRUCTOR(nsThebesRegion)
-NS_GENERIC_FACTORY_CONSTRUCTOR(nsThebesFontEnumerator)
-NS_GENERIC_FACTORY_CONSTRUCTOR(GfxInitialization)
 
 static nsresult
 nsScriptableRegionConstructor(nsISupports *aOuter, REFNSIID aIID, void **aResult)
 {
   nsresult rv;
 
   nsIScriptableRegion *inst = nsnull;
 
@@ -103,34 +101,33 @@ nsScriptableRegionConstructor(nsISupport
   // reference - we don't want this to go out of scope early!
   scriptableRgn = nsnull;
   rv = inst->QueryInterface(aIID, aResult);
   NS_RELEASE(inst);
 
   return rv;
 }
 
+NS_GENERIC_FACTORY_CONSTRUCTOR(GfxInitialization)
+
 NS_DEFINE_NAMED_CID(NS_FONT_ENUMERATOR_CID);
-NS_DEFINE_NAMED_CID(NS_DEVICE_CONTEXT_CID);
 NS_DEFINE_NAMED_CID(NS_REGION_CID);
 NS_DEFINE_NAMED_CID(NS_SCRIPTABLE_REGION_CID);
 NS_DEFINE_NAMED_CID(NS_GFX_INITIALIZATION_CID);
 
 static const mozilla::Module::CIDEntry kThebesCIDs[] = {
     { &kNS_FONT_ENUMERATOR_CID, false, NULL, nsThebesFontEnumeratorConstructor },
-    { &kNS_DEVICE_CONTEXT_CID, false, NULL, nsThebesDeviceContextConstructor },
     { &kNS_REGION_CID, false, NULL, nsThebesRegionConstructor },
     { &kNS_SCRIPTABLE_REGION_CID, false, NULL, nsScriptableRegionConstructor },
     { &kNS_GFX_INITIALIZATION_CID, false, NULL, GfxInitializationConstructor },
     { NULL }
 };
 
 static const mozilla::Module::ContractIDEntry kThebesContracts[] = {
     { "@mozilla.org/gfx/fontenumerator;1", &kNS_FONT_ENUMERATOR_CID },
-    { "@mozilla.org/gfx/devicecontext;1", &kNS_DEVICE_CONTEXT_CID },
     { "@mozilla.org/gfx/region/nsThebes;1", &kNS_REGION_CID },
     { "@mozilla.org/gfx/region;1", &kNS_SCRIPTABLE_REGION_CID },
     { "@mozilla.org/gfx/init;1", &kNS_GFX_INITIALIZATION_CID },
     { NULL }
 };
 
 static const mozilla::Module::CategoryEntry kThebesCategories[] = {
     { "app-startup", "Gfx Initialization", "service,@mozilla.org/gfx/init;1" },
@@ -141,17 +138,17 @@ static nsresult
 nsThebesGfxModuleCtor()
 {
     return gfxPlatform::Init();
 }
 
 static void
 nsThebesGfxModuleDtor()
 {
-    nsThebesDeviceContext::Shutdown();
+    nsDeviceContext::ClearCachedSystemFonts();
     gfxPlatform::Shutdown();
 }
 
 static const mozilla::Module kThebesModule = {
     mozilla::Module::kVersion,
     kThebesCIDs,
     kThebesContracts,
     kThebesCategories,
--- a/gfx/thebes/gfxTypes.h
+++ b/gfx/thebes/gfxTypes.h
@@ -54,17 +54,17 @@ typedef double gfxFloat;
 #else
 # define THEBES_API NS_IMPORT
 #endif
 
 /**
  * gfx errors
  */
 
-/* nsIDeviceContext.h defines a set of printer errors  */
+/* nsIDeviceContextSpec.h defines a set of printer errors  */
 #define NS_ERROR_GFX_GENERAL_BASE (50) 
 
 /* Font cmap is strangely structured - avoid this font! */
 #define NS_ERROR_GFX_CMAP_MALFORMED          \
   NS_ERROR_GENERATE_FAILURE(NS_ERROR_MODULE_GFX,NS_ERROR_GFX_GENERAL_BASE+1)
 
 /**
  * Priority of a line break opportunity.
--- a/layout/base/nsDocumentViewer.cpp
+++ b/layout/base/nsDocumentViewer.cpp
@@ -512,17 +512,16 @@ protected:
   PRPackedBool mHidden;
 };
 
 //------------------------------------------------------------------
 // DocumentViewerImpl
 //------------------------------------------------------------------
 // Class IDs
 static NS_DEFINE_CID(kViewManagerCID,       NS_VIEW_MANAGER_CID);
-static NS_DEFINE_CID(kDeviceContextCID,     NS_DEVICE_CONTEXT_CID);
 
 //------------------------------------------------------------------
 nsresult
 NS_NewDocumentViewer(nsIDocumentViewer** aResult)
 {
   *aResult = new DocumentViewerImpl();
   if (!*aResult) {
     return NS_ERROR_OUT_OF_MEMORY;
@@ -921,33 +920,16 @@ DocumentViewerImpl::InitInternal(nsIWidg
       Hide();
 
 #ifdef NS_PRINT_PREVIEW
       if (mIsPageMode) {
         // I'm leaving this in a broken state for the moment; we should
         // be measuring/scaling with the print device context, not the
         // screen device context, but this is good enough to allow
         // printing reftests to work.
-#if 0
-        nsCOMPtr<nsIDeviceContextSpec> devspec =
-          do_CreateInstance("@mozilla.org/gfx/devicecontextspec;1", &rv);
-        NS_ENSURE_SUCCESS(rv, rv);
-        // mWindow has been initialized by preceding call to MakeWindow
-        rv = devspec->Init(mWindow, mPresContext->GetPrintSettings(), PR_FALSE);
-        NS_ENSURE_SUCCESS(rv, rv);
-        nsCOMPtr<nsIDeviceContext> devctx =
-          do_CreateInstance("@mozilla.org/gfx/devicecontext;1", &rv);
-        NS_ENSURE_SUCCESS(rv, rv);
-        rv = devctx->InitForPrinting(devspec);
-        NS_ENSURE_SUCCESS(rv, rv);
-        // XXX I'm breaking this code; I'm not sure I really want to mess with
-        // the document viewer at the moment to get the right device context
-        // (this won't break anyone, since page layout mode was never really
-        // usable)
-#endif
         double pageWidth = 0, pageHeight = 0;
         mPresContext->GetPrintSettings()->GetEffectivePageSize(&pageWidth,
                                                                &pageHeight);
         mPresContext->SetPageSize(
           nsSize(mPresContext->CSSTwipsToAppUnits(NSToIntFloor(pageWidth)),
                  mPresContext->CSSTwipsToAppUnits(NSToIntFloor(pageHeight))));
         mPresContext->SetIsRootPaginatedDocument(PR_TRUE);
         mPresContext->SetPageScale(1.0f);
@@ -2441,30 +2423,28 @@ DocumentViewerImpl::CreateDeviceContext(
         mDeviceContext = ctx->DeviceContext();
         return NS_OK;
       }
     }
   }
   
   // Create a device context even if we already have one, since our widget
   // might have changed.
-  mDeviceContext = do_CreateInstance(kDeviceContextCID);
-  NS_ENSURE_TRUE(mDeviceContext, NS_ERROR_FAILURE);
   nsIWidget* widget = nsnull;
   if (aContainerView) {
     widget = aContainerView->GetNearestWidget(nsnull);
   }
-  // The device context needs a widget to be able to determine the screen it is on.
   if (!widget) {
     widget = mParentWidget;
   }
   if (widget) {
     widget = widget->GetTopLevelWidget();
   }
 
+  mDeviceContext = new nsDeviceContext();
   mDeviceContext->Init(widget);
   return NS_OK;
 }
 
 // Return the selection for the document. Note that text fields have their
 // own selection, which cannot be accessed with this method.
 nsresult DocumentViewerImpl::GetDocumentSelection(nsISelection **aSelection)
 {
--- a/layout/base/nsPresContext.cpp
+++ b/layout/base/nsPresContext.cpp
@@ -343,17 +343,17 @@ TraverseImageLoader(const void * aKey, n
 
   cb->NoteXPCOMChild(aData);
 
   return PL_DHASH_NEXT;
 }
 
 NS_IMPL_CYCLE_COLLECTION_TRAVERSE_BEGIN(nsPresContext)
   NS_IMPL_CYCLE_COLLECTION_TRAVERSE_NSCOMPTR(mDocument);
-  NS_IMPL_CYCLE_COLLECTION_TRAVERSE_RAWPTR(mDeviceContext); // worth bothering?
+  // NS_IMPL_CYCLE_COLLECTION_TRAVERSE_RAWPTR(mDeviceContext); // not xpcom
   NS_IMPL_CYCLE_COLLECTION_TRAVERSE_RAWPTR(mEventManager);
   // NS_IMPL_CYCLE_COLLECTION_TRAVERSE_RAWPTR(mLookAndFeel); // a service
   // NS_IMPL_CYCLE_COLLECTION_TRAVERSE_RAWPTR(mLanguage); // an atom
 
   for (PRUint32 i = 0; i < IMAGE_LOAD_TYPE_COUNT; ++i)
     tmp->mImageLoaders[i].Enumerate(TraverseImageLoader, &cb);
 
   // NS_IMPL_CYCLE_COLLECTION_TRAVERSE_NSCOMPTR(mTheme); // a service
--- a/layout/printing/nsPrintEngine.cpp
+++ b/layout/printing/nsPrintEngine.cpp
@@ -650,21 +650,20 @@ nsPrintEngine::DoCommonPrint(PRBool     
     if (rv == NS_ERROR_ABORT) 
       return rv;
     NS_ENSURE_SUCCESS(rv, rv);
   }
 
   rv = devspec->Init(nsnull, mPrt->mPrintSettings, aIsPrintPreview);
   NS_ENSURE_SUCCESS(rv, rv);
 
-  mPrt->mPrintDC = do_CreateInstance("@mozilla.org/gfx/devicecontext;1", &rv);
-  NS_ENSURE_SUCCESS(rv, rv);
+  mPrt->mPrintDC = new nsDeviceContext();
   rv = mPrt->mPrintDC->InitForPrinting(devspec);
   NS_ENSURE_SUCCESS(rv, rv);
-  
+
   if (aIsPrintPreview) {
     mPrt->mPrintSettings->SetPrintFrameType(nsIPrintSettings::kFramesAsIs);
 
     // override any UI that wants to PrintPreview any selection or page range
     // we want to view every page in PrintPreview each time
     mPrt->mPrintSettings->SetPrintRange(nsIPrintSettings::kRangeAllPages);
   } else {
     // Always check and set the print settings first and then fall back
--- a/widget/src/gtk2/nsNativeThemeGTK.cpp
+++ b/widget/src/gtk2/nsNativeThemeGTK.cpp
@@ -1240,21 +1240,17 @@ nsNativeThemeGTK::WidgetStateChanged(nsI
   }
 
   return NS_OK;
 }
 
 NS_IMETHODIMP
 nsNativeThemeGTK::ThemeChanged()
 {
-  // this totally sucks.  this method is really supposed to be
-  // static, which is why we can call it without any initialization.
-  static NS_DEFINE_CID(kDeviceContextCID, NS_DEVICE_CONTEXT_CID);
-  nsCOMPtr<nsIDeviceContext> dctx = do_CreateInstance(kDeviceContextCID);
-  dctx->ClearCachedSystemFonts();
+  nsDeviceContext::ClearCachedSystemFonts();
 
   memset(mDisabledWidgetTypes, 0, sizeof(mDisabledWidgetTypes));
   return NS_OK;
 }
 
 NS_IMETHODIMP_(PRBool)
 nsNativeThemeGTK::ThemeSupportsWidget(nsPresContext* aPresContext,
                                       nsIFrame* aFrame,
--- a/widget/src/gtk2/nsWindow.cpp
+++ b/widget/src/gtk2/nsWindow.cpp
@@ -153,19 +153,16 @@ D_DEBUG_DOMAIN( ns_Window, "nsWindow", "
 using namespace mozilla;
 using mozilla::gl::GLContext;
 using mozilla::layers::LayerManagerOGL;
 
 // Don't put more than this many rects in the dirty region, just fluff
 // out to the bounding-box if there are more
 #define MAX_RECTS_IN_REGION 100
 
-/* For PrepareNativeWidget */
-static NS_DEFINE_IID(kDeviceContextCID, NS_DEVICE_CONTEXT_CID);
-
 /* utility functions */
 static PRBool     check_for_rollup(GdkWindow *aWindow,
                                    gdouble aMouseX, gdouble aMouseY,
                                    PRBool aIsWheel, PRBool aAlwaysRollup);
 static PRBool     is_mouse_in_window(GdkWindow* aWindow,
                                      gdouble aMouseX, gdouble aMouseY);
 static nsWindow  *get_window_for_gtk_widget(GtkWidget *widget);
 static nsWindow  *get_window_for_gdk_window(GdkWindow *window);
--- a/widget/src/qt/nsWindow.cpp
+++ b/widget/src/qt/nsWindow.cpp
@@ -151,19 +151,16 @@ static nsRefPtr<gfxASurface> gBufferSurf
 #ifdef MOZ_HAVE_SHMIMAGE
 // If we're using xshm rendering, mThebesSurface wraps gShmImage
 nsRefPtr<nsShmImage> gShmImage;
 #endif
 
 static int gBufferPixmapUsageCount = 0;
 static gfxIntSize gBufferMaxSize(0, 0);
 
-/* For PrepareNativeWidget */
-static NS_DEFINE_IID(kDeviceContextCID, NS_DEVICE_CONTEXT_CID);
-
 // initialization static functions 
 static nsresult    initialize_prefs        (void);
 
 static NS_DEFINE_IID(kCDragServiceCID,  NS_DRAGSERVICE_CID);
 
 #define NS_WINDOW_TITLE_MAX_LENGTH 4095
 
 #define kWindowPositionSlop 20
--- a/widget/src/xpwidgets/nsBaseWidget.cpp
+++ b/widget/src/xpwidgets/nsBaseWidget.cpp
@@ -205,24 +205,19 @@ void nsBaseWidget::BaseCreate(nsIWidget 
   mEventCallback = aHandleEventFunction;
   
   // keep a reference to the device context
   if (aContext) {
     mContext = aContext;
     NS_ADDREF(mContext);
   }
   else {
-    nsresult  res;
-    
-    static NS_DEFINE_CID(kDeviceContextCID, NS_DEVICE_CONTEXT_CID);
-    
-    res = CallCreateInstance(kDeviceContextCID, &mContext);
-
-    if (NS_SUCCEEDED(res))
-      mContext->Init(nsnull);
+    mContext = new nsDeviceContext();
+    NS_ADDREF(mContext);
+    mContext->Init(nsnull);
   }
 
   if (nsnull != aInitData) {
     mWindowType = aInitData->mWindowType;
     mBorderStyle = aInitData->mBorderStyle;
     mPopupLevel = aInitData->mPopupLevel;
   }