Back to index

lightning-sunbird  0.9+nobinonly
nsDrawingSurfaceOS2.cpp
Go to the documentation of this file.
00001 /* ***** BEGIN LICENSE BLOCK *****
00002  * Version: MPL 1.1/GPL 2.0/LGPL 2.1
00003  *
00004  * The contents of this file are subject to the Mozilla Public License Version
00005  * 1.1 (the "License"); you may not use this file except in compliance with
00006  * the License. You may obtain a copy of the License at
00007  * http://www.mozilla.org/MPL/
00008  *
00009  * Software distributed under the License is distributed on an "AS IS" basis,
00010  * WITHOUT WARRANTY OF ANY KIND, either express or implied. See the License
00011  * for the specific language governing rights and limitations under the
00012  * License.
00013  *
00014  * The Original Code is the Mozilla OS/2 libraries.
00015  *
00016  * The Initial Developer of the Original Code is
00017  * John Fairhurst, <john_fairhurst@iname.com>.
00018  * Portions created by the Initial Developer are Copyright (C) 1999
00019  * the Initial Developer. All Rights Reserved.
00020  *
00021  * Contributor(s):
00022  *   Pierre Phaneuf <pp@ludusdesign.com>
00023  *
00024  * Alternatively, the contents of this file may be used under the terms of
00025  * either of the GNU General Public License Version 2 or later (the "GPL"),
00026  * or the GNU Lesser General Public License Version 2.1 or later (the "LGPL"),
00027  * in which case the provisions of the GPL or the LGPL are applicable instead
00028  * of those above. If you wish to allow use of your version of this file only
00029  * under the terms of either the GPL or the LGPL, and not to allow others to
00030  * use your version of this file under the terms of the MPL, indicate your
00031  * decision by deleting the provisions above and replace them with the notice
00032  * and other provisions required by the GPL or the LGPL. If you do not delete
00033  * the provisions above, a recipient may use your version of this file under
00034  * the terms of any one of the MPL, the GPL or the LGPL.
00035  *
00036  * ***** END LICENSE BLOCK ***** */
00037 
00038 #include "nsGfxDefs.h"
00039 #include "nsHashtable.h"
00040 #include "nsIWidget.h"
00041 #include "nsDrawingSurfaceOS2.h"
00042 #include "nsFontMetricsOS2.h"
00043 #include "nsPaletteOS2.h"
00044 
00045 #define LCID_START 2
00046 
00047 
00048 // Base class -- fonts, palette and xpcom -----------------------------------
00049 
00050 NS_IMPL_ISUPPORTS1(nsDrawingSurfaceOS2, nsIDrawingSurface)
00051 
00052 // We start allocated lCIDs at 2.  This leaves #1 for nsFontMetricsOS2 to
00053 // do testing with, and 0 is, of course, LCID_DEFAULT.
00054 
00055 nsDrawingSurfaceOS2::nsDrawingSurfaceOS2()
00056                     : mNextID(LCID_START), mTopID(1), mPS(0), mOwnPS(PR_FALSE),
00057                       mWidth (0), mHeight (0)
00058 {
00059    mHTFonts = new nsHashtable;
00060 }
00061 
00062 nsDrawingSurfaceOS2::~nsDrawingSurfaceOS2()
00063 {
00064    DisposeFonts();
00065 }
00066 
00067 void nsDrawingSurfaceOS2::DisposeFonts()
00068 {
00069    if( mHTFonts)
00070    {
00071       // free font things
00072       GFX (::GpiSetCharSet(mPS, LCID_DEFAULT), FALSE);
00073 
00074       for (int i = LCID_START; i <= mTopID; i++) {
00075          GFX (::GpiDeleteSetId(mPS, i), FALSE);
00076       }
00077       delete mHTFonts;
00078       mHTFonts = 0;
00079    }
00080 }
00081 
00082 // Key for the hashtable
00083 typedef nsVoidKey FontHandleKey;
00084 
00085 void nsDrawingSurfaceOS2::SelectFont(nsFontOS2* aFont)
00086 {
00087    FontHandleKey key((void*)aFont->mHashMe);
00088 
00089    long lcid = (long) mHTFonts->Get(&key);
00090    if (lcid == 0) {
00091       if (mNextID == 255) {
00092          // ids used up, need to empty table and start again.
00093          FlushFontCache();
00094       }
00095 
00096       lcid = mNextID;
00097       mNextID++;
00098       CHK_SUCCESS (::GpiCreateLogFont(mPS, 0, lcid, &aFont->mFattrs),
00099                    FONT_MATCH);
00100       mHTFonts->Put(&key, (void *) lcid);
00101       if (mTopID < 254) {
00102          mTopID++;
00103       }
00104    }
00105 
00106    aFont->SelectIntoPS(mPS, lcid);
00107 }
00108 
00109 void nsDrawingSurfaceOS2::FlushFontCache()
00110 {
00111    mHTFonts->Reset();
00112    mNextID = LCID_START;
00113    // leave mTopID where it is.
00114 }
00115 
00116 // OS/2 - XP coord conversion ----------------------------------------------
00117 
00118 // get inclusive-inclusive rect
00119 void nsDrawingSurfaceOS2::NS2PM_ININ( const nsRect &in, RECTL &rcl)
00120 {
00121    const static nscoord kBottomLeftLimit = -8192;
00122    const static nscoord kTopRightLimit   =  16384;
00123 
00124    PRInt32 ulHeight = GetHeight ();
00125 
00126    rcl.xLeft    = PR_MAX(kBottomLeftLimit, in.x);
00127    rcl.xRight   = PR_MIN(in.x+in.width-1, kTopRightLimit);
00128    rcl.yTop     = PR_MIN(ulHeight-in.y-1, kTopRightLimit);
00129    rcl.yBottom  = PR_MAX(rcl.yTop-in.height+1, kBottomLeftLimit);
00130    return;
00131 }
00132 
00133 void nsDrawingSurfaceOS2::PM2NS_ININ( const RECTL &in, nsRect &out)
00134 {
00135    PRInt32 ulHeight = GetHeight ();
00136 
00137    out.x = in.xLeft;
00138    out.width = in.xRight - in.xLeft + 1;
00139    out.y = ulHeight - in.yTop - 1;
00140    out.height = in.yTop - in.yBottom + 1;
00141 }
00142 
00143 // get in-ex rect
00144 void nsDrawingSurfaceOS2::NS2PM_INEX( const nsRect &in, RECTL &rcl)
00145 {
00146    NS2PM_ININ( in, rcl);
00147    rcl.xRight++;
00148    rcl.yTop++;
00149 }
00150 
00151 void nsDrawingSurfaceOS2::NS2PM( PPOINTL aPointl, ULONG cPointls)
00152 {
00153    PRInt32 ulHeight = GetHeight ();
00154 
00155    for( ULONG i = 0; i < cPointls; i++)
00156       aPointl[ i].y = ulHeight - aPointl[ i].y - 1;
00157 }
00158 
00159 nsresult nsDrawingSurfaceOS2::GetDimensions( PRUint32 *aWidth, PRUint32 *aHeight)
00160 {
00161    if( !aWidth || !aHeight)
00162       return NS_ERROR_NULL_POINTER;
00163 
00164    *aWidth = mWidth;
00165    *aHeight = mHeight;
00166 
00167    return NS_OK;
00168 }
00169 
00170 
00171 // Offscreen surface --------------------------------------------------------
00172 
00173 nsOffscreenSurface::nsOffscreenSurface() : mDC(0), mBitmap(0),
00174                                            mInfoHeader(0), mBits(0),
00175                                            mYPels(0), mScans(0)
00176 {
00177 }
00178 
00179 NS_IMETHODIMP nsOffscreenSurface :: Init(HPS aPS)
00180 {
00181   mPS = aPS;
00182 
00183   return NS_OK;
00184 }
00185 
00186 // Setup a new offscreen surface which is to be compatible with the
00187 // passed-in presentation space.
00188 nsresult nsOffscreenSurface::Init( HPS     aCompatiblePS,
00189                                    PRInt32 aWidth, PRInt32 aHeight, PRUint32 aFlags)
00190 {
00191    nsresult rc = NS_ERROR_FAILURE;
00192 
00193    // Find the compatible device context and create a memory one
00194    HDC hdcCompat = GFX (::GpiQueryDevice (aCompatiblePS), HDC_ERROR);
00195    DEVOPENSTRUC dop = { 0, 0, 0, 0, 0 };
00196    mDC = GFX (::DevOpenDC( 0/*hab*/, OD_MEMORY, "*", 5, (PDEVOPENDATA) &dop, hdcCompat), DEV_ERROR);
00197 
00198    if( DEV_ERROR != mDC)
00199    {
00200       // create the PS
00201       SIZEL sizel = { 0, 0 };
00202       mPS = GFX (::GpiCreatePS (0/*hab*/, mDC, &sizel,
00203                  PU_PELS | GPIT_MICRO | GPIA_ASSOC), GPI_ERROR);
00204 
00205       if( GPI_ERROR != mPS)
00206       {
00207          mOwnPS = PR_TRUE;
00208 
00209          nsPaletteOS2::SelectGlobalPalette(mPS);
00210 
00211          // now create a bitmap of the right size
00212          BITMAPINFOHEADER2 hdr = { 0 };
00213       
00214          hdr.cbFix = sizeof( BITMAPINFOHEADER2);
00215          hdr.cx = aWidth;
00216          hdr.cy = aHeight;
00217          hdr.cPlanes = 1;
00218 
00219          // find bitdepth
00220          LONG lBitCount = 0;
00221          GFX (::DevQueryCaps( hdcCompat, CAPS_COLOR_BITCOUNT, 1, &lBitCount), FALSE);
00222          hdr.cBitCount = (USHORT) lBitCount;
00223 
00224          mBitmap = GFX (::GpiCreateBitmap (mPS, &hdr, 0, 0, 0), GPI_ERROR);
00225 
00226          if( GPI_ERROR != mBitmap)
00227          {
00228             // set final stats & select bitmap into ps
00229             mHeight = aHeight;
00230             mWidth = aWidth;
00231             GFX (::GpiSetBitmap (mPS, mBitmap), HBM_ERROR);
00232             rc = NS_OK;
00233          }
00234       }
00235    }
00236 
00237    return rc;
00238 }
00239 
00240 nsOffscreenSurface::~nsOffscreenSurface()
00241 {
00242    DisposeFonts();
00243    
00244    if (mBitmap) {
00245       GFX (::GpiSetBitmap (mPS, 0), HBM_ERROR);
00246       GFX (::GpiDeleteBitmap (mBitmap), FALSE);
00247    }
00248    if (mOwnPS) {
00249       GFX (::GpiDestroyPS (mPS), FALSE);
00250    }
00251    if (mDC) {
00252       ::DevCloseDC(mDC);
00253    }
00254 
00255    if( mInfoHeader)
00256       free( mInfoHeader);
00257    delete [] mBits;
00258 }
00259 
00260 // Okay; plan here is to get the bits and hope that the fact that we're
00261 // returning an upside-down rectangle doesn't matter.
00262 //
00263 // If it does, then the following needs to be done:
00264 //
00265 //  * undefine the USD flag in libimg
00266 //  * alter the draw code in nsImageOS2 to draw right-way-up
00267 //  * fix the printing case (probably involving an ugly xform)
00268 //
00269 nsresult nsOffscreenSurface::Lock( PRInt32 aX, PRInt32 aY,
00270                                    PRUint32 aWidth, PRUint32 aHeight,
00271                                    void **aBits, PRInt32 *aStride,
00272                                    PRInt32 *aWidthBytes,
00273                                    PRUint32 aFlags)
00274 {
00275    // Trust other platforms to ensure that we don't get nested!
00276    PRInt32 lStride = 0;
00277    ULONG   rc = 0;
00278 
00279    // Allocate buffers first time we get called.
00280    //
00281    // Need to look at the way in which this functionality is exercised:
00282    // may actually be more efficient to only grab the section of bitmap
00283    // required on each call, and to free up memory afterwards.
00284    //
00285    // Currently: * allocate once enough space for the entire bitmap
00286    //            * only grab & set the required scanlines
00287    //
00288    if( !mBits)
00289    {
00290       BITMAPINFOHEADER bih = { sizeof( BITMAPINFOHEADER), 0, 0, 0, 0 };
00291    
00292       rc = GFX (::GpiQueryBitmapInfoHeader (mBitmap, (PBITMAPINFOHEADER2) &bih), FALSE);
00293    
00294       // alloc space to query pel data into...
00295       lStride = RASWIDTH( bih.cx, bih.cBitCount);
00296       mBits = new PRUint8 [ lStride * bih.cy ];
00297    
00298       // ..and colour table too
00299       int cols = -1;
00300       if( bih.cBitCount >= 24) cols = 0;
00301       else cols = 1 << bih.cBitCount;
00302    
00303       int szStruct = sizeof( BITMAPINFOHEADER2) + cols * sizeof( RGB2);
00304    
00305       mInfoHeader = (PBITMAPINFOHEADER2) calloc( szStruct, 1);
00306       mInfoHeader->cbFix = sizeof( BITMAPINFOHEADER2);
00307       mInfoHeader->cx = bih.cx;
00308       mInfoHeader->cy = bih.cy;
00309       mInfoHeader->cPlanes = 1;
00310       mInfoHeader->cBitCount = (USHORT) bih.cBitCount;
00311       // GPI-Ref says these have to be set too...
00312       mInfoHeader->ulCompression = BCA_UNCOMP;
00313       mInfoHeader->usRecording = BRA_BOTTOMUP;
00314       mInfoHeader->usRendering = BRH_NOTHALFTONED; // ...hmm...
00315       mInfoHeader->ulColorEncoding = BCE_RGB;
00316    }
00317    else
00318       lStride = RASWIDTH( mInfoHeader->cx, mInfoHeader->cBitCount);
00319 
00320    // record starting scanline (bottom is 0)
00321    mYPels = mInfoHeader->cy - aY - aHeight;
00322    mScans = aHeight;
00323 
00324    rc = GFX (::GpiQueryBitmapBits (mPS, mYPels, mScans, (PBYTE)mBits,
00325                                    (PBITMAPINFO2)mInfoHeader), GPI_ALTERROR);
00326 
00327 #ifdef DEBUG
00328    if( rc != mScans) {
00329      PMERROR( "GpiQueryBitmapBits");
00330      printf( "Lock, requested %d x %d and got %d x %d\n",
00331              aWidth, aHeight, (int) mInfoHeader->cx, aHeight);
00332    }
00333 #endif
00334 
00335    // Okay.  Now have current state of bitmap in mBits.
00336    *aStride = lStride;
00337    *aBits = (void*) (mBits + (aX * (mInfoHeader->cBitCount >> 3)));
00338    *aWidthBytes = aWidth * (mInfoHeader->cBitCount >> 3);
00339 
00340    return NS_OK;
00341 }
00342 
00343 nsresult nsOffscreenSurface::Unlock()
00344 {
00345    GFX (::GpiSetBitmapBits (mPS, mYPels, mScans, (PBYTE)mBits,
00346                             (PBITMAPINFO2)mInfoHeader), GPI_ALTERROR);
00347 
00348    return NS_OK;
00349 }
00350 
00351 nsresult nsOffscreenSurface::IsOffscreen( PRBool *aOffScreen)
00352 {
00353    if( !aOffScreen)
00354       return NS_ERROR_NULL_POINTER;
00355 
00356    *aOffScreen = PR_TRUE;
00357 
00358    return NS_OK;
00359 }
00360 
00361 nsresult nsOffscreenSurface::IsPixelAddressable( PRBool *aAddressable)
00362 {
00363    if( !aAddressable)
00364       return NS_ERROR_NULL_POINTER;
00365 
00366    *aAddressable = PR_TRUE;
00367 
00368    return NS_OK;
00369 }
00370 
00371 nsresult nsOffscreenSurface::GetPixelFormat( nsPixelFormat *aFormat)
00372 {
00373    if( !aFormat)
00374       return NS_ERROR_NULL_POINTER;
00375 
00376    // Okay.  Who knows what's going on here - we (as wz) currently support
00377    // only 8 and 24 bpp bitmaps; dunno what should be done for 32 bpp,
00378    // even if os/2 supports them.
00379    //
00380    // (prob'ly need to get the FOURCC stuff into the act for 16bpp?)
00381    //
00382    BITMAPINFOHEADER bih = { sizeof( BITMAPINFOHEADER), 0, 0, 0, 0 };
00383    GFX (::GpiQueryBitmapInfoHeader (mBitmap, (PBITMAPINFOHEADER2)&bih), FALSE);
00384 
00385    switch( bih.cBitCount)
00386    {
00387       case 8:
00388          memset( aFormat, 0, sizeof(nsPixelFormat));
00389          break;
00390 
00391       case 16:
00392          aFormat->mRedZeroMask   = 0x001F;
00393          aFormat->mGreenZeroMask = 0x003F;
00394          aFormat->mBlueZeroMask  = 0x001F;
00395          aFormat->mAlphaZeroMask = 0;
00396          aFormat->mRedMask       = 0xF800;
00397          aFormat->mGreenMask     = 0x07E0;
00398          aFormat->mBlueMask      = 0x001F;
00399          aFormat->mAlphaMask     = 0;
00400          aFormat->mRedCount      = 5;
00401          aFormat->mGreenCount    = 6;
00402          aFormat->mBlueCount     = 5;
00403          aFormat->mAlphaCount    = 0;
00404          aFormat->mRedShift      = 11;
00405          aFormat->mGreenShift    = 5;
00406          aFormat->mBlueShift     = 0;
00407          aFormat->mAlphaShift    = 0;
00408          break;
00409 
00410       case 24:
00411          aFormat->mRedZeroMask   = 0x0000FF;
00412          aFormat->mGreenZeroMask = 0x0000FF;
00413          aFormat->mBlueZeroMask  = 0x0000FF;
00414          aFormat->mAlphaZeroMask = 0;
00415          aFormat->mRedMask       = 0x0000FF;
00416          aFormat->mGreenMask     = 0x00FF00;
00417          aFormat->mBlueMask      = 0xFF0000;
00418          aFormat->mAlphaMask     = 0;
00419          aFormat->mRedCount      = 8;
00420          aFormat->mGreenCount    = 8;
00421          aFormat->mBlueCount     = 8;
00422          aFormat->mAlphaCount    = 0;
00423          aFormat->mRedShift      = 0;
00424          aFormat->mGreenShift    = 8;
00425          aFormat->mBlueShift     = 16;
00426          aFormat->mAlphaShift    = 0;
00427          break;
00428 
00429       case 32:
00430          aFormat->mRedZeroMask   = 0x000000FF;
00431          aFormat->mGreenZeroMask = 0x000000FF;
00432          aFormat->mBlueZeroMask  = 0x000000FF;
00433          aFormat->mAlphaZeroMask = 0x000000FF;
00434          aFormat->mRedMask       = 0x00FF0000;
00435          aFormat->mGreenMask     = 0x0000FF00;
00436          aFormat->mBlueMask      = 0x000000FF;
00437          aFormat->mAlphaMask     = 0xFF000000;
00438          aFormat->mRedCount      = 8;
00439          aFormat->mGreenCount    = 8;
00440          aFormat->mBlueCount     = 8;
00441          aFormat->mAlphaCount    = 8;
00442          aFormat->mRedShift      = 16;
00443          aFormat->mGreenShift    = 8;
00444          aFormat->mBlueShift     = 0;
00445          aFormat->mAlphaShift    = 24;
00446          break;
00447 
00448       default:
00449 #ifdef DEBUG
00450          printf( "Bad bit-depth for GetPixelFormat (%d)\n", bih.cBitCount);
00451 #endif
00452          break;
00453    }
00454 
00455    return NS_OK;
00456 }
00457 
00458 // Non-offscreen surfaces, base for window & print --------------------------
00459 nsOnscreenSurface::nsOnscreenSurface() : mProxySurface(nsnull)
00460 {
00461 }
00462 
00463 nsOnscreenSurface::~nsOnscreenSurface()
00464 {
00465    NS_IF_RELEASE(mProxySurface);
00466 }
00467 
00468 void nsOnscreenSurface::EnsureProxy()
00469 {
00470    if( !mProxySurface)
00471    {
00472       PRUint32 width, height;
00473       GetDimensions( &width, &height);
00474 
00475       mProxySurface = new nsOffscreenSurface;
00476       if( NS_SUCCEEDED(mProxySurface->Init( mPS, width, height, NS_CREATEDRAWINGSURFACE_FOR_PIXEL_ACCESS)))
00477       {
00478          NS_ADDREF(mProxySurface);
00479       }
00480       else
00481       {
00482          delete mProxySurface;
00483          mProxySurface = nsnull;
00484       }
00485    }
00486 }
00487 
00488 nsresult nsOnscreenSurface::Lock( PRInt32 aX, PRInt32 aY,
00489                                   PRUint32 aWidth, PRUint32 aHeight,
00490                                   void **aBits, PRInt32 *aStride,
00491                                   PRInt32 *aWidthBytes,
00492                                   PRUint32 aFlags)
00493 {
00494    EnsureProxy();
00495 
00496 #ifdef DEBUG
00497    printf( "Locking through a proxy\n");
00498 #endif
00499 
00500    // blit our 'real' bitmap to the proxy surface
00501    PRUint32 width, height;
00502    GetDimensions( &width, &height);
00503    POINTL pts[3] = { { 0, 0 }, { width, height }, { 0, 0 } };
00504    GFX (::GpiBitBlt (mProxySurface->GetPS (), mPS, 3, pts,
00505                      ROP_SRCCOPY, BBO_OR), GPI_ERROR);
00506 
00507    return mProxySurface->Lock( aX, aY, aWidth, aHeight,
00508                                aBits, aStride, aWidthBytes, aFlags);
00509 }
00510 
00511 nsresult nsOnscreenSurface::Unlock()
00512 {
00513    nsresult rc = mProxySurface->Unlock();
00514 
00515    // blit proxy bitmap back to ours
00516    PRUint32 width, height;
00517    GetDimensions( &width, &height);
00518    POINTL pts[3] = { { 0, 0 }, { width, height }, { 0, 0 } };
00519    GFX (::GpiBitBlt (mPS, mProxySurface->GetPS (), 3, pts,
00520                      ROP_SRCCOPY, BBO_OR), GPI_ERROR);
00521 
00522    return rc;
00523 }
00524 
00525 nsresult nsOnscreenSurface::GetPixelFormat( nsPixelFormat *aFormat)
00526 {
00527    EnsureProxy();
00528    return mProxySurface->GetPixelFormat( aFormat);
00529 }
00530 
00531 nsresult nsOnscreenSurface::IsOffscreen( PRBool *aOffScreen)
00532 {
00533    if( !aOffScreen)
00534       return NS_ERROR_NULL_POINTER;
00535 
00536    *aOffScreen = PR_FALSE;
00537 
00538    return NS_OK;
00539 }
00540 
00541 nsresult nsOnscreenSurface::IsPixelAddressable( PRBool *aAddressable)
00542 {
00543    if( !aAddressable)
00544       return NS_ERROR_NULL_POINTER;
00545 
00546    *aAddressable = PR_FALSE;
00547 
00548    return NS_OK;
00549 }
00550 
00551 // Surface for a PM window --------------------------------------------------
00552 nsWindowSurface::nsWindowSurface() : mWidget(nsnull)
00553 {
00554 }
00555 
00556 nsWindowSurface::~nsWindowSurface()
00557 {
00558    // palette will be deselected in superclass dtor
00559 
00560    // need to do this now because hps is invalid after subsequent free
00561    DisposeFonts();
00562    
00563    // release hps if we had instantiated it
00564    if (mOwnPS) {
00565      mWidget->FreeNativeData( (void*) mPS, NS_NATIVE_GRAPHIC);
00566    }
00567 }
00568 
00569 NS_IMETHODIMP nsWindowSurface::Init(HPS aPS, nsIWidget *aWidget)
00570 {
00571   mPS = aPS;
00572   mWidget = aWidget;
00573 
00574   return NS_OK;
00575 }
00576 
00577 nsresult nsWindowSurface::Init( nsIWidget *aOwner)
00578 {
00579    mWidget = aOwner;
00580    mPS = (HPS) mWidget->GetNativeData( NS_NATIVE_GRAPHIC);
00581    mOwnPS = PR_TRUE;
00582 
00583    return NS_OK;
00584 }
00585 
00586 nsresult nsWindowSurface::GetDimensions( PRUint32 *aWidth, PRUint32 *aHeight)
00587 {
00588    // I don't think we can be more efficient than this, except perhaps by
00589    // doing some kind of `push' of height from the window to us.
00590    nsRect rect;
00591    mWidget->GetClientBounds( rect);
00592    *aHeight = rect.height;
00593    *aWidth = rect.width;
00594    return NS_OK;
00595 }
00596 
00597 PRUint32 nsWindowSurface::GetHeight () 
00598 { 
00599    nsRect rect;
00600 
00601    mWidget->GetClientBounds (rect);
00602 
00603    return rect.height;
00604 }
00605 
00606 // Printer surface.  A few minor differences, like the page size is fixed ---
00607 nsPrintSurface::nsPrintSurface()
00608 {
00609 }
00610 
00611 nsresult nsPrintSurface::Init( HPS aPS, PRInt32 aWidth, PRInt32 aHeight, PRUint32 aFlags)
00612 {
00613    mPS = aPS;
00614    mHeight = aHeight;
00615    mWidth = aWidth;
00616 
00617    return NS_OK;
00618 }
00619 
00620 nsPrintSurface::~nsPrintSurface()
00621 {
00622    // PS is owned by the DC; superclass dtor will deselect palette.
00623 }