LCOV - code coverage report
Current view: top level - vcl/source/gdi - bitmap.cxx (source / functions) Hit Total Coverage
Test: commit c8344322a7af75b84dd3ca8f78b05543a976dfd5 Lines: 521 1040 50.1 %
Date: 2015-06-13 12:38:46 Functions: 32 43 74.4 %
Legend: Lines: hit not hit

          Line data    Source code
       1             : /* -*- Mode: C++; tab-width: 4; indent-tabs-mode: nil; c-basic-offset: 4 -*- */
       2             : /*
       3             :  * This file is part of the LibreOffice project.
       4             :  *
       5             :  * This Source Code Form is subject to the terms of the Mozilla Public
       6             :  * License, v. 2.0. If a copy of the MPL was not distributed with this
       7             :  * file, You can obtain one at http://mozilla.org/MPL/2.0/.
       8             :  *
       9             :  * This file incorporates work covered by the following license notice:
      10             :  *
      11             :  *   Licensed to the Apache Software Foundation (ASF) under one or more
      12             :  *   contributor license agreements. See the NOTICE file distributed
      13             :  *   with this work for additional information regarding copyright
      14             :  *   ownership. The ASF licenses this file to you under the Apache
      15             :  *   License, Version 2.0 (the "License"); you may not use this file
      16             :  *   except in compliance with the License. You may obtain a copy of
      17             :  *   the License at http://www.apache.org/licenses/LICENSE-2.0 .
      18             :  */
      19             : 
      20             : #include <algorithm>
      21             : #include <rtl/crc.h>
      22             : #include <tools/stream.hxx>
      23             : #include <tools/poly.hxx>
      24             : #include <tools/rc.h>
      25             : #include <vcl/salbtype.hxx>
      26             : #include <vcl/bmpacc.hxx>
      27             : #include <vcl/outdev.hxx>
      28             : #include <vcl/bitmap.hxx>
      29             : #include <vcl/bitmapex.hxx>
      30             : #include <vcl/svapp.hxx>
      31             : #include <vcl/image.hxx>
      32             : 
      33             : #include <impbmp.hxx>
      34             : #include <salbmp.hxx>
      35             : #include <boost/scoped_array.hpp>
      36             : 
      37     3025180 : Bitmap::Bitmap() :
      38     3025180 :     mpImpBmp( NULL )
      39             : {
      40     3025180 : }
      41             : 
      42        3547 : Bitmap::Bitmap( const ResId& rResId ) :
      43        3547 :     mpImpBmp( NULL )
      44             : {
      45        3547 :     const BitmapEx aBmpEx( rResId );
      46             : 
      47        3547 :     if( !aBmpEx.IsEmpty() )
      48        3547 :         *this = aBmpEx.GetBitmap();
      49        3547 : }
      50             : 
      51     2698500 : Bitmap::Bitmap( const Bitmap& rBitmap ) :
      52             :     maPrefMapMode   ( rBitmap.maPrefMapMode ),
      53     2698500 :     maPrefSize      ( rBitmap.maPrefSize )
      54             : {
      55     2698500 :     mpImpBmp = rBitmap.mpImpBmp;
      56             : 
      57     2698500 :     if ( mpImpBmp )
      58     1876811 :         mpImpBmp->ImplIncRefCount();
      59     2698500 : }
      60             : 
      61           0 : Bitmap::Bitmap( SalBitmap* pSalBitmap )
      62             : {
      63           0 :     mpImpBmp = new ImpBitmap(pSalBitmap);
      64           0 :     maPrefMapMode = MapMode( MAP_PIXEL );
      65           0 :     maPrefSize = mpImpBmp->ImplGetSize();
      66           0 : }
      67             : 
      68       72759 : Bitmap::Bitmap( const Size& rSizePixel, sal_uInt16 nBitCount, const BitmapPalette* pPal )
      69             : {
      70       72759 :     if( rSizePixel.Width() && rSizePixel.Height() )
      71             :     {
      72       72759 :         BitmapPalette   aPal;
      73       72759 :         BitmapPalette*  pRealPal = NULL;
      74             : 
      75       72759 :         if( nBitCount <= 8 )
      76             :         {
      77       51122 :             if( !pPal )
      78             :             {
      79        4076 :                 if( 1 == nBitCount )
      80             :                 {
      81        1534 :                     aPal.SetEntryCount( 2 );
      82        1534 :                     aPal[ 0 ] = Color( COL_BLACK );
      83        1534 :                     aPal[ 1 ] = Color( COL_WHITE );
      84             :                 }
      85        2542 :                 else if( ( 4 == nBitCount ) || ( 8 == nBitCount ) )
      86             :                 {
      87        2542 :                     aPal.SetEntryCount( 1 << nBitCount );
      88        2542 :                     aPal[ 0 ] = Color( COL_BLACK );
      89        2542 :                     aPal[ 1 ] = Color( COL_BLUE );
      90        2542 :                     aPal[ 2 ] = Color( COL_GREEN );
      91        2542 :                     aPal[ 3 ] = Color( COL_CYAN );
      92        2542 :                     aPal[ 4 ] = Color( COL_RED );
      93        2542 :                     aPal[ 5 ] = Color( COL_MAGENTA );
      94        2542 :                     aPal[ 6 ] = Color( COL_BROWN );
      95        2542 :                     aPal[ 7 ] = Color( COL_GRAY );
      96        2542 :                     aPal[ 8 ] = Color( COL_LIGHTGRAY );
      97        2542 :                     aPal[ 9 ] = Color( COL_LIGHTBLUE );
      98        2542 :                     aPal[ 10 ] = Color( COL_LIGHTGREEN );
      99        2542 :                     aPal[ 11 ] = Color( COL_LIGHTCYAN );
     100        2542 :                     aPal[ 12 ] = Color( COL_LIGHTRED );
     101        2542 :                     aPal[ 13 ] = Color( COL_LIGHTMAGENTA );
     102        2542 :                     aPal[ 14 ] = Color( COL_YELLOW );
     103        2542 :                     aPal[ 15 ] = Color( COL_WHITE );
     104             : 
     105             :                     // Create dither palette
     106        2542 :                     if( 8 == nBitCount )
     107             :                     {
     108        2430 :                         sal_uInt16 nActCol = 16;
     109             : 
     110       17010 :                         for( sal_uInt16 nB = 0; nB < 256; nB += 51 )
     111      102060 :                             for( sal_uInt16 nG = 0; nG < 256; nG += 51 )
     112      612360 :                                 for( sal_uInt16 nR = 0; nR < 256; nR += 51 )
     113      524880 :                                     aPal[ nActCol++ ] = BitmapColor( (sal_uInt8) nR, (sal_uInt8) nG, (sal_uInt8) nB );
     114             : 
     115             :                         // Set standard Office colors
     116        2430 :                         aPal[ nActCol++ ] = BitmapColor( 0, 184, 255 );
     117             :                     }
     118             :                 }
     119             :             }
     120             :             else
     121       47046 :                 pRealPal = const_cast<BitmapPalette*>(pPal);
     122             :         }
     123             : 
     124       72759 :         mpImpBmp = new ImpBitmap;
     125       72759 :         mpImpBmp->ImplCreate( rSizePixel, nBitCount, pRealPal ? *pRealPal : aPal );
     126             :     }
     127             :     else
     128           0 :         mpImpBmp = NULL;
     129       72759 : }
     130             : 
     131    11517611 : Bitmap::~Bitmap()
     132             : {
     133     5750878 :     ImplReleaseRef();
     134     5766733 : }
     135             : 
     136      219983 : const BitmapPalette& Bitmap::GetGreyPalette( int nEntries )
     137             : {
     138      219983 :     static BitmapPalette aGreyPalette2;
     139      219983 :     static BitmapPalette aGreyPalette4;
     140      219983 :     static BitmapPalette aGreyPalette16;
     141      219983 :     static BitmapPalette aGreyPalette256;
     142             : 
     143             :     // Create greyscale palette with 2, 4, 16 or 256 entries
     144      219983 :     if( 2 == nEntries || 4 == nEntries || 16 == nEntries || 256 == nEntries )
     145             :     {
     146      219983 :         if( 2 == nEntries )
     147             :         {
     148           0 :             if( !aGreyPalette2.GetEntryCount() )
     149             :             {
     150           0 :                 aGreyPalette2.SetEntryCount( 2 );
     151           0 :                 aGreyPalette2[ 0 ] = BitmapColor( 0, 0, 0 );
     152           0 :                 aGreyPalette2[ 1 ] = BitmapColor( 255, 255, 255 );
     153             :             }
     154             : 
     155           0 :             return aGreyPalette2;
     156             :         }
     157      219983 :         else if( 4 == nEntries )
     158             :         {
     159           0 :             if( !aGreyPalette4.GetEntryCount() )
     160             :             {
     161           0 :                 aGreyPalette4.SetEntryCount( 4 );
     162           0 :                 aGreyPalette4[ 0 ] = BitmapColor( 0, 0, 0 );
     163           0 :                 aGreyPalette4[ 1 ] = BitmapColor( 85, 85, 85 );
     164           0 :                 aGreyPalette4[ 2 ] = BitmapColor( 170, 170, 170 );
     165           0 :                 aGreyPalette4[ 3 ] = BitmapColor( 255, 255, 255 );
     166             :             }
     167             : 
     168           0 :             return aGreyPalette4;
     169             :         }
     170      219983 :         else if( 16 == nEntries )
     171             :         {
     172           2 :             if( !aGreyPalette16.GetEntryCount() )
     173             :             {
     174           1 :                 sal_uInt8 cGrey = 0, cGreyInc = 17;
     175             : 
     176           1 :                 aGreyPalette16.SetEntryCount( 16 );
     177             : 
     178          17 :                 for( sal_uInt16 i = 0; i < 16; i++, cGrey = sal::static_int_cast<sal_uInt8>(cGrey + cGreyInc) )
     179          16 :                     aGreyPalette16[ i ] = BitmapColor( cGrey, cGrey, cGrey );
     180             :             }
     181             : 
     182           2 :             return aGreyPalette16;
     183             :         }
     184             :         else
     185             :         {
     186      219981 :             if( !aGreyPalette256.GetEntryCount() )
     187             :             {
     188         123 :                 aGreyPalette256.SetEntryCount( 256 );
     189             : 
     190       31611 :                 for( sal_uInt16 i = 0; i < 256; i++ )
     191       31488 :                     aGreyPalette256[ i ] = BitmapColor( (sal_uInt8) i, (sal_uInt8) i, (sal_uInt8) i );
     192             :             }
     193             : 
     194      219981 :             return aGreyPalette256;
     195             :         }
     196             :     }
     197             :     else
     198             :     {
     199             :         OSL_FAIL( "Bitmap::GetGreyPalette: invalid entry count (2/4/16/256 allowed)" );
     200           0 :         return aGreyPalette2;
     201             :     }
     202             : }
     203             : 
     204         912 : bool BitmapPalette::IsGreyPalette() const
     205             : {
     206         912 :     const int nEntryCount = GetEntryCount();
     207         912 :     if( !nEntryCount ) // NOTE: an empty palette means 1:1 mapping
     208           0 :         return true;
     209             :     // See above: only certain entry values will result in a valid call to GetGreyPalette
     210         912 :     if( nEntryCount == 2 || nEntryCount == 4 || nEntryCount == 16 || nEntryCount == 256 )
     211             :     {
     212         912 :         const BitmapPalette& rGreyPalette = Bitmap::GetGreyPalette( nEntryCount );
     213         912 :         if( rGreyPalette == *this )
     214         887 :             return true;
     215             :     }
     216             : 
     217          25 :     bool bRet = false;
     218             :     // TODO: is it worth to compare the entries for the general case?
     219          25 :     if (nEntryCount == 2)
     220             :     {
     221           0 :        const BitmapColor& rCol0(mpBitmapColor[0]);
     222           0 :        const BitmapColor& rCol1(mpBitmapColor[1]);
     223           0 :        bRet = rCol0.GetRed() == rCol0.GetGreen() && rCol0.GetRed() == rCol0.GetBlue() &&
     224           0 :               rCol1.GetRed() == rCol1.GetGreen() && rCol1.GetRed() == rCol1.GetBlue();
     225             :     }
     226          25 :     return bRet;
     227             : }
     228             : 
     229     2068602 : Bitmap& Bitmap::operator=( const Bitmap& rBitmap )
     230             : {
     231     2068602 :     if (this == &rBitmap)
     232           0 :         return *this;
     233             : 
     234     2068602 :     maPrefSize = rBitmap.maPrefSize;
     235     2068602 :     maPrefMapMode = rBitmap.maPrefMapMode;
     236             : 
     237     2068602 :     if ( rBitmap.mpImpBmp )
     238     2045794 :         rBitmap.mpImpBmp->ImplIncRefCount();
     239             : 
     240     2068602 :     ImplReleaseRef();
     241     2068602 :     mpImpBmp = rBitmap.mpImpBmp;
     242             : 
     243     2068602 :     return *this;
     244             : }
     245             : 
     246           0 : bool Bitmap::IsEqual( const Bitmap& rBmp ) const
     247             : {
     248           0 :     return( IsSameInstance( rBmp ) ||
     249           0 :             ( rBmp.GetSizePixel() == GetSizePixel() &&
     250           0 :               rBmp.GetBitCount() == GetBitCount() &&
     251           0 :               rBmp.GetChecksum() == GetChecksum() ) );
     252             : }
     253             : 
     254      776053 : void Bitmap::SetEmpty()
     255             : {
     256      776053 :     maPrefMapMode = MapMode();
     257      776053 :     maPrefSize = Size();
     258             : 
     259      776053 :     ImplReleaseRef();
     260      776053 :     mpImpBmp = NULL;
     261      776053 : }
     262             : 
     263      886580 : Size Bitmap::GetSizePixel() const
     264             : {
     265      886580 :     return( mpImpBmp ? mpImpBmp->ImplGetSize() : Size() );
     266             : }
     267             : 
     268      362901 : sal_uInt16 Bitmap::GetBitCount() const
     269             : {
     270      362901 :     return( mpImpBmp ? mpImpBmp->ImplGetBitCount() : 0 );
     271             : }
     272             : 
     273         912 : bool Bitmap::HasGreyPalette() const
     274             : {
     275         912 :     const sal_uInt16    nBitCount = GetBitCount();
     276         912 :     bool            bRet = nBitCount == 1;
     277             : 
     278         912 :     BitmapInfoAccess* pIAcc = const_cast<Bitmap*>(this)->AcquireInfoAccess();
     279             : 
     280         912 :     if( pIAcc )
     281             :     {
     282         912 :         bRet = pIAcc->HasPalette() && pIAcc->GetPalette().IsGreyPalette();
     283         912 :         ReleaseAccess( pIAcc );
     284             :     }
     285             : 
     286         912 :     return bRet;
     287             : }
     288             : 
     289        4653 : sal_uLong Bitmap::GetChecksum() const
     290             : {
     291        4653 :     sal_uLong nRet = 0UL;
     292             : 
     293        4653 :     if( mpImpBmp )
     294             :     {
     295        4653 :         nRet = mpImpBmp->ImplGetChecksum();
     296             : 
     297        4653 :         if( !nRet )
     298             :         {
     299        1623 :             BitmapReadAccess* pRAcc = const_cast<Bitmap*>(this)->AcquireReadAccess();
     300             : 
     301        1623 :             if( pRAcc && pRAcc->Width() && pRAcc->Height() )
     302             :             {
     303        1623 :                 sal_uInt32  nCrc = 0;
     304             :                 SVBT32      aBT32;
     305             : 
     306        1623 :                 pRAcc->ImplZeroInitUnusedBits();
     307             : 
     308        1623 :                 UInt32ToSVBT32( pRAcc->Width(), aBT32 );
     309        1623 :                 nCrc = rtl_crc32( nCrc, aBT32, 4 );
     310             : 
     311        1623 :                 UInt32ToSVBT32( pRAcc->Height(), aBT32 );
     312        1623 :                 nCrc = rtl_crc32( nCrc, aBT32, 4 );
     313             : 
     314        1623 :                 UInt32ToSVBT32( pRAcc->GetBitCount(), aBT32 );
     315        1623 :                 nCrc = rtl_crc32( nCrc, aBT32, 4 );
     316             : 
     317        1623 :                 UInt32ToSVBT32( pRAcc->GetColorMask().GetRedMask(), aBT32 );
     318        1623 :                 nCrc = rtl_crc32( nCrc, aBT32, 4 );
     319             : 
     320        1623 :                 UInt32ToSVBT32( pRAcc->GetColorMask().GetGreenMask(), aBT32 );
     321        1623 :                 nCrc = rtl_crc32( nCrc, aBT32, 4 );
     322             : 
     323        1623 :                 UInt32ToSVBT32( pRAcc->GetColorMask().GetBlueMask(), aBT32 );
     324        1623 :                 nCrc = rtl_crc32( nCrc, aBT32, 4 );
     325             : 
     326        1623 :                 if( pRAcc->HasPalette() )
     327             :                 {
     328         944 :                     nCrc = rtl_crc32( nCrc, pRAcc->GetPalette().ImplGetColorBuffer(),
     329        1888 :                                       pRAcc->GetPaletteEntryCount() * sizeof( BitmapColor ) );
     330             :                 }
     331             : 
     332        1623 :                 nCrc = rtl_crc32( nCrc, pRAcc->GetBuffer(), pRAcc->GetScanlineSize() * pRAcc->Height() );
     333             : 
     334        1623 :                 mpImpBmp->ImplSetChecksum( nRet = nCrc );
     335             :             }
     336             : 
     337        1623 :             if (pRAcc) ReleaseAccess( pRAcc );
     338             :         }
     339             :     }
     340             : 
     341        4653 :     return nRet;
     342             : }
     343             : 
     344     8771569 : void Bitmap::ImplReleaseRef()
     345             : {
     346     8771569 :     if( mpImpBmp )
     347             :     {
     348     4137345 :         if( mpImpBmp->ImplGetRefCount() > 1UL )
     349     3861876 :             mpImpBmp->ImplDecRefCount();
     350             :         else
     351             :         {
     352      275469 :             delete mpImpBmp;
     353      275469 :             mpImpBmp = NULL;
     354             :         }
     355             :     }
     356     8771569 : }
     357             : 
     358      382077 : void Bitmap::ImplMakeUnique()
     359             : {
     360      382077 :     if( mpImpBmp && mpImpBmp->ImplGetRefCount() > 1UL )
     361             :     {
     362       30689 :         ImpBitmap* pOldImpBmp = mpImpBmp;
     363             : 
     364       30689 :         pOldImpBmp->ImplDecRefCount();
     365             : 
     366       30689 :         mpImpBmp = new ImpBitmap;
     367       30689 :         mpImpBmp->ImplCreate( *pOldImpBmp );
     368             :     }
     369      382077 : }
     370             : 
     371        4258 : void Bitmap::ImplAssignWithSize( const Bitmap& rBitmap )
     372             : {
     373        4258 :     const Size      aOldSizePix( GetSizePixel() );
     374        4258 :     const Size      aNewSizePix( rBitmap.GetSizePixel() );
     375        4258 :     const MapMode   aOldMapMode( maPrefMapMode );
     376        4258 :     Size            aNewPrefSize;
     377             : 
     378        4258 :     if( ( aOldSizePix != aNewSizePix ) && aOldSizePix.Width() && aOldSizePix.Height() )
     379             :     {
     380        4257 :         aNewPrefSize.Width() = FRound( maPrefSize.Width() * aNewSizePix.Width() / aOldSizePix.Width() );
     381        4257 :         aNewPrefSize.Height() = FRound( maPrefSize.Height() * aNewSizePix.Height() / aOldSizePix.Height() );
     382             :     }
     383             :     else
     384           1 :         aNewPrefSize = maPrefSize;
     385             : 
     386        4258 :     *this = rBitmap;
     387             : 
     388        4258 :     maPrefSize = aNewPrefSize;
     389        4258 :     maPrefMapMode = aOldMapMode;
     390        4258 : }
     391             : 
     392             : 
     393      176036 : void Bitmap::ImplSetImpBitmap( ImpBitmap* pImpBmp )
     394             : {
     395      176036 :     if( pImpBmp != mpImpBmp )
     396             :     {
     397      176036 :         ImplReleaseRef();
     398      176036 :         mpImpBmp = pImpBmp;
     399             :     }
     400      176036 : }
     401             : 
     402         912 : BitmapInfoAccess* Bitmap::AcquireInfoAccess()
     403             : {
     404         912 :     BitmapInfoAccess* pInfoAccess = new BitmapInfoAccess( *this );
     405             : 
     406         912 :     if( !*pInfoAccess )
     407             :     {
     408           0 :         delete pInfoAccess;
     409           0 :         pInfoAccess = NULL;
     410             :     }
     411             : 
     412         912 :     return pInfoAccess;
     413             : }
     414             : 
     415      504490 : BitmapReadAccess* Bitmap::AcquireReadAccess()
     416             : {
     417      504490 :     BitmapReadAccess* pReadAccess = new BitmapReadAccess( *this );
     418             : 
     419      504490 :     if( !*pReadAccess )
     420             :     {
     421           1 :         delete pReadAccess;
     422           1 :         pReadAccess = NULL;
     423             :     }
     424             : 
     425      504490 :     return pReadAccess;
     426             : }
     427             : 
     428      382077 : BitmapWriteAccess* Bitmap::AcquireWriteAccess()
     429             : {
     430      382077 :     BitmapWriteAccess* pWriteAccess = new BitmapWriteAccess( *this );
     431             : 
     432      382077 :     if( !*pWriteAccess )
     433             :     {
     434           3 :         delete pWriteAccess;
     435           3 :         pWriteAccess = NULL;
     436             :     }
     437             : 
     438      382077 :     return pWriteAccess;
     439             : }
     440             : 
     441      887323 : void Bitmap::ReleaseAccess( BitmapInfoAccess* pBitmapAccess )
     442             : {
     443      887323 :     delete pBitmapAccess;
     444      887323 : }
     445             : 
     446       24535 : bool Bitmap::Erase(const Color& rFillColor)
     447             : {
     448       24535 :     if (IsEmpty())
     449           0 :         return true;
     450             : 
     451       24535 :     Bitmap::ScopedWriteAccess  pWriteAcc(*this);
     452       24535 :     bool bRet = false;
     453             : 
     454       24535 :     if (pWriteAcc)
     455             :     {
     456       24535 :         const sal_uLong nFormat = pWriteAcc->GetScanlineFormat();
     457       24535 :         sal_uInt8 cIndex = 0;
     458       24535 :         bool bFast = false;
     459             : 
     460       24535 :         switch (nFormat)
     461             :         {
     462             :             case BMP_FORMAT_1BIT_MSB_PAL:
     463             :             case BMP_FORMAT_1BIT_LSB_PAL:
     464             :             {
     465         380 :                 cIndex = static_cast<sal_uInt8>(pWriteAcc->GetBestPaletteIndex(rFillColor));
     466         380 :                 cIndex = (cIndex ? 255 : 0);
     467         380 :                 bFast = true;
     468             :             }
     469         380 :             break;
     470             : 
     471             :             case BMP_FORMAT_4BIT_MSN_PAL:
     472             :             case BMP_FORMAT_4BIT_LSN_PAL:
     473             :             {
     474          20 :                 cIndex = static_cast<sal_uInt8>(pWriteAcc->GetBestPaletteIndex(rFillColor));
     475          20 :                 cIndex = cIndex | ( cIndex << 4 );
     476          20 :                 bFast = true;
     477             :             }
     478          20 :             break;
     479             : 
     480             :             case BMP_FORMAT_8BIT_PAL:
     481             :             {
     482       23540 :                 cIndex = static_cast<sal_uInt8>(pWriteAcc->GetBestPaletteIndex(rFillColor));
     483       23540 :                 bFast = true;
     484             :             }
     485       23540 :             break;
     486             : 
     487             :             case BMP_FORMAT_24BIT_TC_BGR:
     488             :             case BMP_FORMAT_24BIT_TC_RGB:
     489             :             {
     490           0 :                 if (rFillColor.GetRed() == rFillColor.GetGreen() &&
     491           0 :                     rFillColor.GetRed() == rFillColor.GetBlue())
     492             :                 {
     493           0 :                     cIndex = rFillColor.GetRed();
     494           0 :                     bFast = true;
     495             :                 }
     496             :                 else
     497           0 :                     bFast = false;
     498             :             }
     499           0 :             break;
     500             : 
     501             :             default:
     502         595 :                 bFast = false;
     503         595 :             break;
     504             :         }
     505             : 
     506       24535 :         if( bFast )
     507             :         {
     508       23940 :             const sal_uLong nBufSize = pWriteAcc->GetScanlineSize() * pWriteAcc->Height();
     509       23940 :             memset( pWriteAcc->GetBuffer(), cIndex, nBufSize );
     510             :         }
     511             :         else
     512             :         {
     513         595 :             Point aTmpPoint;
     514         595 :             const Rectangle aRect( aTmpPoint, Size( pWriteAcc->Width(), pWriteAcc->Height() ) );
     515         595 :             pWriteAcc->SetFillColor( rFillColor );
     516         595 :             pWriteAcc->FillRect( aRect );
     517             :         }
     518             : 
     519       24535 :         bRet = true;
     520             :     }
     521             : 
     522       24535 :     return bRet;
     523             : }
     524             : 
     525          22 : bool Bitmap::Invert()
     526             : {
     527          22 :     BitmapWriteAccess*  pAcc = AcquireWriteAccess();
     528          22 :     bool                bRet = false;
     529             : 
     530          22 :     if( pAcc )
     531             :     {
     532          22 :         if( pAcc->HasPalette() )
     533             :         {
     534          17 :             BitmapPalette   aBmpPal( pAcc->GetPalette() );
     535          17 :             const sal_uInt16    nCount = aBmpPal.GetEntryCount();
     536             : 
     537          51 :             for( sal_uInt16 i = 0; i < nCount; i++ )
     538          34 :                 aBmpPal[ i ].Invert();
     539             : 
     540          17 :             pAcc->SetPalette( aBmpPal );
     541             :         }
     542             :         else
     543             :         {
     544           5 :             const long  nWidth = pAcc->Width();
     545           5 :             const long  nHeight = pAcc->Height();
     546             : 
     547         165 :             for( long nX = 0L; nX < nWidth; nX++ )
     548        5280 :                 for( long nY = 0L; nY < nHeight; nY++ )
     549        5120 :                     pAcc->SetPixel( nY, nX, pAcc->GetPixel( nY, nX ).Invert() );
     550             :         }
     551             : 
     552          22 :         ReleaseAccess( pAcc );
     553          22 :         bRet = true;
     554             :     }
     555             : 
     556          22 :     return bRet;
     557             : }
     558             : 
     559           0 : bool Bitmap::Mirror( BmpMirrorFlags nMirrorFlags )
     560             : {
     561           0 :     bool bHorz( nMirrorFlags & BmpMirrorFlags::Horizontal );
     562           0 :     bool bVert( nMirrorFlags & BmpMirrorFlags::Vertical );
     563           0 :     bool bRet = false;
     564             : 
     565           0 :     if( bHorz && !bVert )
     566             :     {
     567           0 :         BitmapWriteAccess*  pAcc = AcquireWriteAccess();
     568             : 
     569           0 :         if( pAcc )
     570             :         {
     571           0 :             const long  nWidth = pAcc->Width();
     572           0 :             const long  nHeight = pAcc->Height();
     573           0 :             const long  nWidth1 = nWidth - 1L;
     574           0 :             const long  nWidth_2 = nWidth >> 1L;
     575             : 
     576           0 :             for( long nY = 0L; nY < nHeight; nY++ )
     577             :             {
     578           0 :                 for( long nX = 0L, nOther = nWidth1; nX < nWidth_2; nX++, nOther-- )
     579             :                 {
     580           0 :                     const BitmapColor aTemp( pAcc->GetPixel( nY, nX ) );
     581             : 
     582           0 :                     pAcc->SetPixel( nY, nX, pAcc->GetPixel( nY, nOther ) );
     583           0 :                     pAcc->SetPixel( nY, nOther, aTemp );
     584           0 :                 }
     585             :             }
     586             : 
     587           0 :             ReleaseAccess( pAcc );
     588           0 :             bRet = true;
     589           0 :         }
     590             :     }
     591           0 :     else if( bVert && !bHorz )
     592             :     {
     593           0 :         BitmapWriteAccess*  pAcc = AcquireWriteAccess();
     594             : 
     595           0 :         if( pAcc )
     596             :         {
     597           0 :             const long  nScanSize = pAcc->GetScanlineSize();
     598           0 :             boost::scoped_array<sal_uInt8> pBuffer(new sal_uInt8[ nScanSize ]);
     599           0 :             const long  nHeight = pAcc->Height();
     600           0 :             const long  nHeight1 = nHeight - 1L;
     601           0 :             const long  nHeight_2 = nHeight >> 1L;
     602             : 
     603           0 :             for( long nY = 0L, nOther = nHeight1; nY < nHeight_2; nY++, nOther-- )
     604             :             {
     605           0 :                 memcpy( pBuffer.get(), pAcc->GetScanline( nY ), nScanSize );
     606           0 :                 memcpy( pAcc->GetScanline( nY ), pAcc->GetScanline( nOther ), nScanSize );
     607           0 :                 memcpy( pAcc->GetScanline( nOther ), pBuffer.get(), nScanSize );
     608             :             }
     609             : 
     610           0 :             ReleaseAccess( pAcc );
     611           0 :             bRet = true;
     612           0 :         }
     613             :     }
     614           0 :     else if( bHorz && bVert )
     615             :     {
     616           0 :         BitmapWriteAccess*  pAcc = AcquireWriteAccess();
     617             : 
     618           0 :         if( pAcc )
     619             :         {
     620           0 :             const long  nWidth = pAcc->Width();
     621           0 :             const long  nWidth1 = nWidth - 1L;
     622           0 :             const long  nHeight = pAcc->Height();
     623           0 :             long        nHeight_2 = nHeight >> 1;
     624             : 
     625           0 :             for( long nY = 0L, nOtherY = nHeight - 1L; nY < nHeight_2; nY++, nOtherY-- )
     626             :             {
     627           0 :                 for( long nX = 0L, nOtherX = nWidth1; nX < nWidth; nX++, nOtherX-- )
     628             :                 {
     629           0 :                     const BitmapColor aTemp( pAcc->GetPixel( nY, nX ) );
     630             : 
     631           0 :                     pAcc->SetPixel( nY, nX, pAcc->GetPixel( nOtherY, nOtherX ) );
     632           0 :                     pAcc->SetPixel( nOtherY, nOtherX, aTemp );
     633           0 :                 }
     634             :             }
     635             : 
     636             :             // ggf. noch mittlere Zeile horizontal spiegeln
     637           0 :             if( nHeight & 1 )
     638             :             {
     639           0 :                 for( long nX = 0L, nOtherX = nWidth1, nWidth_2 = nWidth >> 1; nX < nWidth_2; nX++, nOtherX-- )
     640             :                 {
     641           0 :                     const BitmapColor aTemp( pAcc->GetPixel( nHeight_2, nX ) );
     642           0 :                     pAcc->SetPixel( nHeight_2, nX, pAcc->GetPixel( nHeight_2, nOtherX ) );
     643           0 :                     pAcc->SetPixel( nHeight_2, nOtherX, aTemp );
     644           0 :                 }
     645             :             }
     646             : 
     647           0 :             ReleaseAccess( pAcc );
     648           0 :             bRet = true;
     649           0 :         }
     650             :     }
     651             :     else
     652           0 :         bRet = true;
     653             : 
     654           0 :     return bRet;
     655             : }
     656             : 
     657           0 : bool Bitmap::Rotate( long nAngle10, const Color& rFillColor )
     658             : {
     659           0 :     bool bRet = false;
     660             : 
     661           0 :     nAngle10 %= 3600L;
     662           0 :     nAngle10 = ( nAngle10 < 0L ) ? ( 3599L + nAngle10 ) : nAngle10;
     663             : 
     664           0 :     if( !nAngle10    )
     665           0 :         bRet = true;
     666           0 :     else if( 1800L == nAngle10 )
     667           0 :         bRet = Mirror( BmpMirrorFlags::Horizontal | BmpMirrorFlags::Vertical );
     668             :     else
     669             :     {
     670           0 :         BitmapReadAccess*   pReadAcc = AcquireReadAccess();
     671           0 :         Bitmap              aRotatedBmp;
     672             : 
     673           0 :         if( pReadAcc )
     674             :         {
     675           0 :             const Size  aSizePix( GetSizePixel() );
     676             : 
     677           0 :             if( ( 900L == nAngle10 ) || ( 2700L == nAngle10 ) )
     678             :             {
     679           0 :                 const Size          aNewSizePix( aSizePix.Height(), aSizePix.Width() );
     680           0 :                 Bitmap              aNewBmp( aNewSizePix, GetBitCount(), &pReadAcc->GetPalette() );
     681           0 :                 BitmapWriteAccess*  pWriteAcc = aNewBmp.AcquireWriteAccess();
     682             : 
     683           0 :                 if( pWriteAcc )
     684             :                 {
     685           0 :                     const long  nWidth = aSizePix.Width();
     686           0 :                     const long  nWidth1 = nWidth - 1L;
     687           0 :                     const long  nHeight = aSizePix.Height();
     688           0 :                     const long  nHeight1 = nHeight - 1L;
     689           0 :                     const long  nNewWidth = aNewSizePix.Width();
     690           0 :                     const long  nNewHeight = aNewSizePix.Height();
     691             : 
     692           0 :                     if( 900L == nAngle10 )
     693             :                     {
     694           0 :                         for( long nY = 0L, nOtherX = nWidth1; nY < nNewHeight; nY++, nOtherX-- )
     695           0 :                             for( long nX = 0L, nOtherY = 0L; nX < nNewWidth; nX++ )
     696           0 :                                 pWriteAcc->SetPixel( nY, nX, pReadAcc->GetPixel( nOtherY++, nOtherX ) );
     697             :                     }
     698           0 :                     else if( 2700L == nAngle10 )
     699             :                     {
     700           0 :                         for( long nY = 0L, nOtherX = 0L; nY < nNewHeight; nY++, nOtherX++ )
     701           0 :                             for( long nX = 0L, nOtherY = nHeight1; nX < nNewWidth; nX++ )
     702           0 :                                 pWriteAcc->SetPixel( nY, nX, pReadAcc->GetPixel( nOtherY--, nOtherX ) );
     703             :                     }
     704             : 
     705           0 :                     ReleaseAccess( pWriteAcc );
     706             :                 }
     707             : 
     708           0 :                 aRotatedBmp = aNewBmp;
     709             :             }
     710             :             else
     711             :             {
     712           0 :                 Point       aTmpPoint;
     713           0 :                 Rectangle   aTmpRectangle( aTmpPoint, aSizePix );
     714           0 :                 Polygon     aPoly( aTmpRectangle );
     715           0 :                 aPoly.Rotate( aTmpPoint, (sal_uInt16) nAngle10 );
     716             : 
     717           0 :                 Rectangle           aNewBound( aPoly.GetBoundRect() );
     718           0 :                 const Size          aNewSizePix( aNewBound.GetSize() );
     719           0 :                 Bitmap              aNewBmp( aNewSizePix, GetBitCount(), &pReadAcc->GetPalette() );
     720           0 :                 BitmapWriteAccess*  pWriteAcc = aNewBmp.AcquireWriteAccess();
     721             : 
     722           0 :                 if( pWriteAcc )
     723             :                 {
     724           0 :                     const BitmapColor   aFillColor( pWriteAcc->GetBestMatchingColor( rFillColor ) );
     725           0 :                     const double        fCosAngle = cos( nAngle10 * F_PI1800 );
     726           0 :                     const double        fSinAngle = sin( nAngle10 * F_PI1800 );
     727           0 :                     const double        fXMin = aNewBound.Left();
     728           0 :                     const double        fYMin = aNewBound.Top();
     729           0 :                     const long          nWidth = aSizePix.Width();
     730           0 :                     const long          nHeight = aSizePix.Height();
     731           0 :                     const long          nNewWidth = aNewSizePix.Width();
     732           0 :                     const long          nNewHeight = aNewSizePix.Height();
     733             :                     long                nX;
     734             :                     long                nY;
     735             :                     long                nRotX;
     736             :                     long                nRotY;
     737           0 :                     boost::scoped_array<long> pCosX(new long[ nNewWidth ]);
     738           0 :                     boost::scoped_array<long> pSinX(new long[ nNewWidth ]);
     739           0 :                     boost::scoped_array<long> pCosY(new long[ nNewHeight ]);
     740           0 :                     boost::scoped_array<long> pSinY(new long[ nNewHeight ]);
     741             : 
     742           0 :                     for ( nX = 0; nX < nNewWidth; nX++ )
     743             :                     {
     744           0 :                         const double fTmp = ( fXMin + nX ) * 64.;
     745             : 
     746           0 :                         pCosX[ nX ] = FRound( fCosAngle * fTmp );
     747           0 :                         pSinX[ nX ] = FRound( fSinAngle * fTmp );
     748             :                     }
     749             : 
     750           0 :                     for ( nY = 0; nY < nNewHeight; nY++ )
     751             :                     {
     752           0 :                         const double fTmp = ( fYMin + nY ) * 64.;
     753             : 
     754           0 :                         pCosY[ nY ] = FRound( fCosAngle * fTmp );
     755           0 :                         pSinY[ nY ] = FRound( fSinAngle * fTmp );
     756             :                     }
     757             : 
     758           0 :                     for( nY = 0L; nY < nNewHeight; nY++ )
     759             :                     {
     760           0 :                         long nSinY = pSinY[ nY ];
     761           0 :                         long nCosY = pCosY[ nY ];
     762             : 
     763           0 :                         for( nX = 0L; nX < nNewWidth; nX++ )
     764             :                         {
     765           0 :                             nRotX = ( pCosX[ nX ] - nSinY ) >> 6;
     766           0 :                             nRotY = ( pSinX[ nX ] + nCosY ) >> 6;
     767             : 
     768           0 :                             if ( ( nRotX > -1L ) && ( nRotX < nWidth ) && ( nRotY > -1L ) && ( nRotY < nHeight ) )
     769           0 :                                 pWriteAcc->SetPixel( nY, nX, pReadAcc->GetPixel( nRotY, nRotX ) );
     770             :                             else
     771           0 :                                 pWriteAcc->SetPixel( nY, nX, aFillColor );
     772             :                         }
     773             :                     }
     774             : 
     775           0 :                     ReleaseAccess( pWriteAcc );
     776             :                 }
     777             : 
     778           0 :                 aRotatedBmp = aNewBmp;
     779             :             }
     780             : 
     781           0 :             ReleaseAccess( pReadAcc );
     782             :         }
     783             : 
     784           0 :         if( ( bRet = !!aRotatedBmp ) )
     785           0 :             ImplAssignWithSize( aRotatedBmp );
     786             :     }
     787             : 
     788           0 :     return bRet;
     789             : };
     790             : 
     791        1818 : bool Bitmap::Crop( const Rectangle& rRectPixel )
     792             : {
     793        1818 :     const Size          aSizePix( GetSizePixel() );
     794        1818 :     Rectangle           aRect( rRectPixel );
     795        1818 :     bool                bRet = false;
     796             : 
     797        1818 :     aRect.Intersection( Rectangle( Point(), aSizePix ) );
     798             : 
     799        1818 :     if( !aRect.IsEmpty() && aSizePix != aRect.GetSize())
     800             :     {
     801        1765 :         BitmapReadAccess* pReadAcc = AcquireReadAccess();
     802             : 
     803        1765 :         if( pReadAcc )
     804             :         {
     805        1765 :             Point               aTmpPoint;
     806        1765 :             const Rectangle     aNewRect( aTmpPoint, aRect.GetSize() );
     807        1765 :             Bitmap              aNewBmp( aNewRect.GetSize(), GetBitCount(), &pReadAcc->GetPalette() );
     808        1765 :             BitmapWriteAccess*  pWriteAcc = aNewBmp.AcquireWriteAccess();
     809             : 
     810        1765 :             if( pWriteAcc )
     811             :             {
     812        1765 :                 const long nOldX = aRect.Left();
     813        1765 :                 const long nOldY = aRect.Top();
     814        1765 :                 const long nNewWidth = aNewRect.GetWidth();
     815        1765 :                 const long nNewHeight = aNewRect.GetHeight();
     816             : 
     817       20865 :                 for( long nY = 0, nY2 = nOldY; nY < nNewHeight; nY++, nY2++ )
     818      292920 :                     for( long nX = 0, nX2 = nOldX; nX < nNewWidth; nX++, nX2++ )
     819      273820 :                         pWriteAcc->SetPixel( nY, nX, pReadAcc->GetPixel( nY2, nX2 ) );
     820             : 
     821        1765 :                 ReleaseAccess( pWriteAcc );
     822        1765 :                 bRet = true;
     823             :             }
     824             : 
     825        1765 :             ReleaseAccess( pReadAcc );
     826             : 
     827        1765 :             if( bRet )
     828        1765 :                 ImplAssignWithSize( aNewBmp );
     829             :         }
     830             :     }
     831             : 
     832        1818 :     return bRet;
     833             : };
     834             : 
     835       11553 : bool Bitmap::CopyPixel( const Rectangle& rRectDst,
     836             :                         const Rectangle& rRectSrc, const Bitmap* pBmpSrc )
     837             : {
     838       11553 :     const Size  aSizePix( GetSizePixel() );
     839       11553 :     Rectangle   aRectDst( rRectDst );
     840       11553 :     bool        bRet = false;
     841             : 
     842       11553 :     aRectDst.Intersection( Rectangle( Point(), aSizePix ) );
     843             : 
     844       11553 :     if( !aRectDst.IsEmpty() )
     845             :     {
     846       11553 :         if( pBmpSrc && ( *pBmpSrc != *this ) )
     847             :         {
     848       11553 :             Bitmap*         pSrc = const_cast<Bitmap*>(pBmpSrc);
     849       11553 :             const Size      aCopySizePix( pSrc->GetSizePixel() );
     850       11553 :             Rectangle       aRectSrc( rRectSrc );
     851       11553 :             const sal_uInt16    nSrcBitCount = pBmpSrc->GetBitCount();
     852       11553 :             const sal_uInt16    nDstBitCount = GetBitCount();
     853             : 
     854       11553 :             if( nSrcBitCount > nDstBitCount )
     855             :             {
     856           0 :                 long nNextIndex = 0L;
     857             : 
     858           0 :                 if( ( nSrcBitCount == 24 ) && ( nDstBitCount < 24 ) )
     859           0 :                     Convert( BMP_CONVERSION_24BIT );
     860           0 :                 else if( ( nSrcBitCount == 8 ) && ( nDstBitCount < 8 ) )
     861             :                 {
     862           0 :                     Convert( BMP_CONVERSION_8BIT_COLORS );
     863           0 :                     nNextIndex = 16;
     864             :                 }
     865           0 :                 else if( ( nSrcBitCount == 4 ) && ( nDstBitCount < 4 ) )
     866             :                 {
     867           0 :                     Convert( BMP_CONVERSION_4BIT_COLORS );
     868           0 :                     nNextIndex = 2;
     869             :                 }
     870             : 
     871           0 :                 if( nNextIndex )
     872             :                 {
     873           0 :                     BitmapReadAccess*   pSrcAcc = pSrc->AcquireReadAccess();
     874           0 :                     BitmapWriteAccess*  pDstAcc = AcquireWriteAccess();
     875             : 
     876           0 :                     if( pSrcAcc && pDstAcc )
     877             :                     {
     878           0 :                         const long      nSrcCount = pDstAcc->GetPaletteEntryCount();
     879           0 :                         const long      nDstCount = 1 << nDstBitCount;
     880             : 
     881           0 :                         for( long i = 0L; ( i < nSrcCount ) && ( nNextIndex < nSrcCount ); i++ )
     882             :                         {
     883           0 :                             const BitmapColor& rSrcCol = pSrcAcc->GetPaletteColor( (sal_uInt16) i );
     884             : 
     885           0 :                             bool bFound = false;
     886             : 
     887           0 :                             for( long j = 0L; j < nDstCount; j++ )
     888             :                             {
     889           0 :                                 if( rSrcCol == pDstAcc->GetPaletteColor( (sal_uInt16) j ) )
     890             :                                 {
     891           0 :                                     bFound = true;
     892           0 :                                     break;
     893             :                                 }
     894             :                             }
     895             : 
     896           0 :                             if( !bFound )
     897           0 :                                 pDstAcc->SetPaletteColor( (sal_uInt16) nNextIndex++, rSrcCol );
     898             :                         }
     899             :                     }
     900             : 
     901           0 :                     if( pSrcAcc )
     902           0 :                         ReleaseAccess( pSrcAcc );
     903             : 
     904           0 :                     if( pDstAcc )
     905           0 :                         ReleaseAccess( pDstAcc );
     906             :                 }
     907             :             }
     908             : 
     909       11553 :             aRectSrc.Intersection( Rectangle( Point(), aCopySizePix ) );
     910             : 
     911       11553 :             if( !aRectSrc.IsEmpty() )
     912             :             {
     913       11553 :                 BitmapReadAccess* pReadAcc = pSrc->AcquireReadAccess();
     914             : 
     915       11553 :                 if( pReadAcc )
     916             :                 {
     917       11553 :                     BitmapWriteAccess* pWriteAcc = AcquireWriteAccess();
     918             : 
     919       11553 :                     if( pWriteAcc )
     920             :                     {
     921       11553 :                         const long  nWidth = std::min( aRectSrc.GetWidth(), aRectDst.GetWidth() );
     922       11553 :                         const long  nHeight = std::min( aRectSrc.GetHeight(), aRectDst.GetHeight() );
     923       11553 :                         const long  nSrcEndX = aRectSrc.Left() + nWidth;
     924       11553 :                         const long  nSrcEndY = aRectSrc.Top() + nHeight;
     925       11553 :                         long        nDstY = aRectDst.Top();
     926             : 
     927       11553 :                         if( pReadAcc->HasPalette() && pWriteAcc->HasPalette() )
     928             :                         {
     929        5735 :                             const sal_uInt16    nCount = pReadAcc->GetPaletteEntryCount();
     930        5735 :                             boost::scoped_array<sal_uInt8> pMap(new sal_uInt8[ nCount ]);
     931             : 
     932             :                             // Create index map for the color table, as the bitmap should be copied
     933             :                             // retaining it's color information relatively well
     934     1390705 :                             for( sal_uInt16 i = 0; i < nCount; i++ )
     935     1384970 :                                 pMap[ i ] = (sal_uInt8) pWriteAcc->GetBestPaletteIndex( pReadAcc->GetPaletteColor( i ) );
     936             : 
     937       52497 :                             for( long nSrcY = aRectSrc.Top(); nSrcY < nSrcEndY; nSrcY++, nDstY++ )
     938      475764 :                                 for( long nSrcX = aRectSrc.Left(), nDstX = aRectDst.Left(); nSrcX < nSrcEndX; nSrcX++, nDstX++ )
     939      434737 :                                     pWriteAcc->SetPixelIndex( nDstY, nDstX, pMap[ pReadAcc->GetPixelIndex( nSrcY, nSrcX ) ] );
     940             :                         }
     941        5818 :                         else if( pReadAcc->HasPalette() )
     942             :                         {
     943           0 :                             for( long nSrcY = aRectSrc.Top(); nSrcY < nSrcEndY; nSrcY++, nDstY++ )
     944           0 :                                 for( long nSrcX = aRectSrc.Left(), nDstX = aRectDst.Left(); nSrcX < nSrcEndX; nSrcX++, nDstX++ )
     945           0 :                                     pWriteAcc->SetPixel( nDstY, nDstX, pReadAcc->GetPaletteColor( pReadAcc->GetPixelIndex( nSrcY, nSrcX ) ) );
     946             :                         }
     947             :                         else
     948       80666 :                             for( long nSrcY = aRectSrc.Top(); nSrcY < nSrcEndY; nSrcY++, nDstY++ )
     949     1905152 :                                 for( long nSrcX = aRectSrc.Left(), nDstX = aRectDst.Left(); nSrcX < nSrcEndX; nSrcX++, nDstX++ )
     950     1830304 :                                     pWriteAcc->SetPixel( nDstY, nDstX, pReadAcc->GetPixel( nSrcY, nSrcX ) );
     951             : 
     952       11553 :                         ReleaseAccess( pWriteAcc );
     953       11553 :                         bRet = ( nWidth > 0L ) && ( nHeight > 0L );
     954             :                     }
     955             : 
     956       11553 :                     ReleaseAccess( pReadAcc );
     957             :                 }
     958             :             }
     959             :         }
     960             :         else
     961             :         {
     962           0 :             Rectangle aRectSrc( rRectSrc );
     963             : 
     964           0 :             aRectSrc.Intersection( Rectangle( Point(), aSizePix ) );
     965             : 
     966           0 :             if( !aRectSrc.IsEmpty() && ( aRectSrc != aRectDst ) )
     967             :             {
     968           0 :                 BitmapWriteAccess*  pWriteAcc = AcquireWriteAccess();
     969             : 
     970           0 :                 if( pWriteAcc )
     971             :                 {
     972           0 :                     const long  nWidth = std::min( aRectSrc.GetWidth(), aRectDst.GetWidth() );
     973           0 :                     const long  nHeight = std::min( aRectSrc.GetHeight(), aRectDst.GetHeight() );
     974           0 :                     const long  nSrcX = aRectSrc.Left();
     975           0 :                     const long  nSrcY = aRectSrc.Top();
     976           0 :                     const long  nSrcEndX1 = nSrcX + nWidth - 1L;
     977           0 :                     const long  nSrcEndY1 = nSrcY + nHeight - 1L;
     978           0 :                     const long  nDstX = aRectDst.Left();
     979           0 :                     const long  nDstY = aRectDst.Top();
     980           0 :                     const long  nDstEndX1 = nDstX + nWidth - 1L;
     981           0 :                     const long  nDstEndY1 = nDstY + nHeight - 1L;
     982             : 
     983           0 :                     if( ( nDstX <= nSrcX ) && ( nDstY <= nSrcY ) )
     984             :                     {
     985           0 :                         for( long nY = nSrcY, nYN = nDstY; nY <= nSrcEndY1; nY++, nYN++ )
     986           0 :                             for( long nX = nSrcX, nXN = nDstX; nX <= nSrcEndX1; nX++, nXN++ )
     987           0 :                                 pWriteAcc->SetPixel( nYN, nXN, pWriteAcc->GetPixel( nY, nX ) );
     988             :                     }
     989           0 :                     else if( ( nDstX <= nSrcX ) && ( nDstY >= nSrcY ) )
     990             :                     {
     991           0 :                         for( long nY = nSrcEndY1, nYN = nDstEndY1; nY >= nSrcY; nY--, nYN-- )
     992           0 :                             for( long nX = nSrcX, nXN = nDstX; nX <= nSrcEndX1; nX++, nXN++ )
     993           0 :                                 pWriteAcc->SetPixel( nYN, nXN, pWriteAcc->GetPixel( nY, nX ) );
     994             :                     }
     995           0 :                     else if( ( nDstX >= nSrcX ) && ( nDstY <= nSrcY ) )
     996             :                     {
     997           0 :                         for( long nY = nSrcY, nYN = nDstY; nY <= nSrcEndY1; nY++, nYN++ )
     998           0 :                             for( long nX = nSrcEndX1, nXN = nDstEndX1; nX >= nSrcX; nX--, nXN-- )
     999           0 :                                 pWriteAcc->SetPixel( nYN, nXN, pWriteAcc->GetPixel( nY, nX ) );
    1000             :                     }
    1001             :                     else
    1002             :                     {
    1003           0 :                         for( long nY = nSrcEndY1, nYN = nDstEndY1; nY >= nSrcY; nY--, nYN-- )
    1004           0 :                             for( long nX = nSrcEndX1, nXN = nDstEndX1; nX >= nSrcX; nX--, nXN-- )
    1005           0 :                                 pWriteAcc->SetPixel( nYN, nXN, pWriteAcc->GetPixel( nY, nX ) );
    1006             :                     }
    1007             : 
    1008           0 :                     ReleaseAccess( pWriteAcc );
    1009           0 :                     bRet = true;
    1010             :                 }
    1011             :             }
    1012             :         }
    1013             :     }
    1014             : 
    1015       11553 :     return bRet;
    1016             : }
    1017             : 
    1018        6915 : bool Bitmap::CopyPixel_AlphaOptimized( const Rectangle& rRectDst, const Rectangle& rRectSrc,
    1019             :                            const Bitmap* pBmpSrc )
    1020             : {
    1021             :     // Note: this code is copied from Bitmap::CopyPixel but avoids any palette lookups
    1022             :     // This optimization is possible because the palettes of AlphaMasks are always identical (8bit GreyPalette, see ctor)
    1023        6915 :     const Size  aSizePix( GetSizePixel() );
    1024        6915 :     Rectangle   aRectDst( rRectDst );
    1025        6915 :     bool        bRet = false;
    1026             : 
    1027        6915 :     aRectDst.Intersection( Rectangle( Point(), aSizePix ) );
    1028             : 
    1029        6915 :     if( !aRectDst.IsEmpty() )
    1030             :     {
    1031        6915 :         if( pBmpSrc && ( *pBmpSrc != *this ) )
    1032             :         {
    1033        6915 :             Bitmap*         pSrc = const_cast<Bitmap*>(pBmpSrc);
    1034        6915 :             const Size      aCopySizePix( pSrc->GetSizePixel() );
    1035        6915 :             Rectangle       aRectSrc( rRectSrc );
    1036             : 
    1037        6915 :             aRectSrc.Intersection( Rectangle( Point(), aCopySizePix ) );
    1038             : 
    1039        6915 :             if( !aRectSrc.IsEmpty() )
    1040             :             {
    1041        6915 :                 BitmapReadAccess* pReadAcc = pSrc->AcquireReadAccess();
    1042             : 
    1043        6915 :                 if( pReadAcc )
    1044             :                 {
    1045        6915 :                     BitmapWriteAccess* pWriteAcc = AcquireWriteAccess();
    1046             : 
    1047        6915 :                     if( pWriteAcc )
    1048             :                     {
    1049        6915 :                         const long  nWidth = std::min( aRectSrc.GetWidth(), aRectDst.GetWidth() );
    1050        6915 :                         const long  nHeight = std::min( aRectSrc.GetHeight(), aRectDst.GetHeight() );
    1051        6915 :                         const long  nSrcEndX = aRectSrc.Left() + nWidth;
    1052        6915 :                         const long  nSrcEndY = aRectSrc.Top() + nHeight;
    1053        6915 :                         long        nDstY = aRectDst.Top();
    1054             : 
    1055       92507 :                         for( long nSrcY = aRectSrc.Top(); nSrcY < nSrcEndY; nSrcY++, nDstY++ )
    1056     1983992 :                             for( long nSrcX = aRectSrc.Left(), nDstX = aRectDst.Left(); nSrcX < nSrcEndX; nSrcX++, nDstX++ )
    1057     1898400 :                                 pWriteAcc->SetPixel( nDstY, nDstX, pReadAcc->GetPixel( nSrcY, nSrcX ) );
    1058             : 
    1059        6915 :                         ReleaseAccess( pWriteAcc );
    1060        6915 :                         bRet = ( nWidth > 0L ) && ( nHeight > 0L );
    1061             :                     }
    1062             : 
    1063        6915 :                     ReleaseAccess( pReadAcc );
    1064             :                 }
    1065             :             }
    1066             :         }
    1067             :         else
    1068             :         {
    1069           0 :             Rectangle aRectSrc( rRectSrc );
    1070             : 
    1071           0 :             aRectSrc.Intersection( Rectangle( Point(), aSizePix ) );
    1072             : 
    1073           0 :             if( !aRectSrc.IsEmpty() && ( aRectSrc != aRectDst ) )
    1074             :             {
    1075           0 :                 BitmapWriteAccess*  pWriteAcc = AcquireWriteAccess();
    1076             : 
    1077           0 :                 if( pWriteAcc )
    1078             :                 {
    1079           0 :                     const long  nWidth = std::min( aRectSrc.GetWidth(), aRectDst.GetWidth() );
    1080           0 :                     const long  nHeight = std::min( aRectSrc.GetHeight(), aRectDst.GetHeight() );
    1081           0 :                     const long  nSrcX = aRectSrc.Left();
    1082           0 :                     const long  nSrcY = aRectSrc.Top();
    1083           0 :                     const long  nSrcEndX1 = nSrcX + nWidth - 1L;
    1084           0 :                     const long  nSrcEndY1 = nSrcY + nHeight - 1L;
    1085           0 :                     const long  nDstX = aRectDst.Left();
    1086           0 :                     const long  nDstY = aRectDst.Top();
    1087           0 :                     const long  nDstEndX1 = nDstX + nWidth - 1L;
    1088           0 :                     const long  nDstEndY1 = nDstY + nHeight - 1L;
    1089             : 
    1090           0 :                     if( ( nDstX <= nSrcX ) && ( nDstY <= nSrcY ) )
    1091             :                     {
    1092           0 :                         for( long nY = nSrcY, nYN = nDstY; nY <= nSrcEndY1; nY++, nYN++ )
    1093           0 :                             for( long nX = nSrcX, nXN = nDstX; nX <= nSrcEndX1; nX++, nXN++ )
    1094           0 :                                 pWriteAcc->SetPixel( nYN, nXN, pWriteAcc->GetPixel( nY, nX ) );
    1095             :                     }
    1096           0 :                     else if( ( nDstX <= nSrcX ) && ( nDstY >= nSrcY ) )
    1097             :                     {
    1098           0 :                         for( long nY = nSrcEndY1, nYN = nDstEndY1; nY >= nSrcY; nY--, nYN-- )
    1099           0 :                             for( long nX = nSrcX, nXN = nDstX; nX <= nSrcEndX1; nX++, nXN++ )
    1100           0 :                                 pWriteAcc->SetPixel( nYN, nXN, pWriteAcc->GetPixel( nY, nX ) );
    1101             :                     }
    1102           0 :                     else if( ( nDstX >= nSrcX ) && ( nDstY <= nSrcY ) )
    1103             :                     {
    1104           0 :                         for( long nY = nSrcY, nYN = nDstY; nY <= nSrcEndY1; nY++, nYN++ )
    1105           0 :                             for( long nX = nSrcEndX1, nXN = nDstEndX1; nX >= nSrcX; nX--, nXN-- )
    1106           0 :                                 pWriteAcc->SetPixel( nYN, nXN, pWriteAcc->GetPixel( nY, nX ) );
    1107             :                     }
    1108             :                     else
    1109             :                     {
    1110           0 :                         for( long nY = nSrcEndY1, nYN = nDstEndY1; nY >= nSrcY; nY--, nYN-- )
    1111           0 :                             for( long nX = nSrcEndX1, nXN = nDstEndX1; nX >= nSrcX; nX--, nXN-- )
    1112           0 :                                 pWriteAcc->SetPixel( nYN, nXN, pWriteAcc->GetPixel( nY, nX ) );
    1113             :                     }
    1114             : 
    1115           0 :                     ReleaseAccess( pWriteAcc );
    1116           0 :                     bRet = true;
    1117             :                 }
    1118             :             }
    1119             :         }
    1120             :     }
    1121             : 
    1122        6915 :     return bRet;
    1123             : 
    1124             : }
    1125             : 
    1126           0 : bool Bitmap::Expand( sal_uLong nDX, sal_uLong nDY, const Color* pInitColor )
    1127             : {
    1128           0 :     bool bRet = false;
    1129             : 
    1130           0 :     if( nDX || nDY )
    1131             :     {
    1132           0 :         const Size          aSizePixel( GetSizePixel() );
    1133           0 :         const long          nWidth = aSizePixel.Width();
    1134           0 :         const long          nHeight = aSizePixel.Height();
    1135           0 :         const Size          aNewSize( nWidth + nDX, nHeight + nDY );
    1136           0 :         BitmapReadAccess*   pReadAcc = AcquireReadAccess();
    1137             : 
    1138           0 :         if( pReadAcc )
    1139             :         {
    1140           0 :             BitmapPalette       aBmpPal( pReadAcc->GetPalette() );
    1141           0 :             Bitmap              aNewBmp( aNewSize, GetBitCount(), &aBmpPal );
    1142           0 :             BitmapWriteAccess*  pWriteAcc = aNewBmp.AcquireWriteAccess();
    1143             : 
    1144           0 :             if( pWriteAcc )
    1145             :             {
    1146           0 :                 BitmapColor aColor;
    1147           0 :                 const long  nNewX = nWidth;
    1148           0 :                 const long  nNewY = nHeight;
    1149           0 :                 const long  nNewWidth = pWriteAcc->Width();
    1150           0 :                 const long  nNewHeight = pWriteAcc->Height();
    1151             :                 long        nX;
    1152             :                 long        nY;
    1153             : 
    1154           0 :                 if( pInitColor )
    1155           0 :                     aColor = pWriteAcc->GetBestMatchingColor( *pInitColor );
    1156             : 
    1157           0 :                 for( nY = 0L; nY < nHeight; nY++ )
    1158             :                 {
    1159           0 :                     pWriteAcc->CopyScanline( nY, *pReadAcc );
    1160             : 
    1161           0 :                     if( pInitColor && nDX )
    1162           0 :                         for( nX = nNewX; nX < nNewWidth; nX++ )
    1163           0 :                             pWriteAcc->SetPixel( nY, nX, aColor );
    1164             :                 }
    1165             : 
    1166           0 :                 if( pInitColor && nDY )
    1167           0 :                     for( nY = nNewY; nY < nNewHeight; nY++ )
    1168           0 :                         for( nX = 0; nX < nNewWidth; nX++ )
    1169           0 :                             pWriteAcc->SetPixel( nY, nX, aColor );
    1170             : 
    1171           0 :                 ReleaseAccess( pWriteAcc );
    1172           0 :                 bRet = true;
    1173             :             }
    1174             : 
    1175           0 :             ReleaseAccess( pReadAcc );
    1176             : 
    1177           0 :             if( bRet )
    1178           0 :                 ImplAssignWithSize( aNewBmp );
    1179             :         }
    1180             :     }
    1181             : 
    1182           0 :     return bRet;
    1183             : }
    1184             : 
    1185          49 : Bitmap Bitmap::CreateMask( const Color& rTransColor, sal_uLong nTol ) const
    1186             : {
    1187          49 :     Bitmap              aNewBmp( GetSizePixel(), 1 );
    1188          49 :     BitmapWriteAccess*  pWriteAcc = aNewBmp.AcquireWriteAccess();
    1189          49 :     bool                bRet = false;
    1190             : 
    1191          49 :     if( pWriteAcc )
    1192             :     {
    1193          49 :         BitmapReadAccess* pReadAcc = const_cast<Bitmap*>(this)->AcquireReadAccess();
    1194             : 
    1195          49 :         if( pReadAcc )
    1196             :         {
    1197          49 :             const long          nWidth = pReadAcc->Width();
    1198          49 :             const long          nHeight = pReadAcc->Height();
    1199          49 :             const BitmapColor   aBlack( pWriteAcc->GetBestMatchingColor( Color( COL_BLACK ) ) );
    1200          98 :             const BitmapColor   aWhite( pWriteAcc->GetBestMatchingColor( Color( COL_WHITE ) ) );
    1201             : 
    1202          49 :             if( !nTol )
    1203             :             {
    1204          45 :                 const BitmapColor   aTest( pReadAcc->GetBestMatchingColor( rTransColor ) );
    1205             :                 long nX, nY;
    1206             : 
    1207          84 :                 if( pReadAcc->GetScanlineFormat() == BMP_FORMAT_4BIT_MSN_PAL ||
    1208          39 :                     pReadAcc->GetScanlineFormat() == BMP_FORMAT_4BIT_LSN_PAL )
    1209             :                 {
    1210             :                     // optimized for 4Bit-MSN/LSN source palette
    1211           6 :                     const sal_uInt8 cTest = aTest.GetIndex();
    1212           6 :                     const long nShiftInit = ( ( pReadAcc->GetScanlineFormat() == BMP_FORMAT_4BIT_MSN_PAL ) ? 4 : 0 );
    1213             : 
    1214          12 :                     if( pWriteAcc->GetScanlineFormat() == BMP_FORMAT_1BIT_MSB_PAL &&
    1215           6 :                         aWhite.GetIndex() == 1 )
    1216             :                     {
    1217             :                         // optimized for 1Bit-MSB destination palette
    1218          84 :                         for( nY = 0L; nY < nHeight; nY++ )
    1219             :                         {
    1220          78 :                             Scanline pSrc = pReadAcc->GetScanline( nY );
    1221          78 :                             Scanline pDst = pWriteAcc->GetScanline( nY );
    1222          78 :                             long nShift = 0;
    1223        7683 :                             for( nX = 0L, nShift = nShiftInit; nX < nWidth; nX++, nShift ^= 4 )
    1224             :                             {
    1225        7605 :                                 if( cTest == ( ( pSrc[ nX >> 1 ] >> nShift ) & 0x0f ) )
    1226        1026 :                                     pDst[ nX >> 3 ] |= 1 << ( 7 - ( nX & 7 ) );
    1227             :                                 else
    1228        6579 :                                     pDst[ nX >> 3 ] &= ~( 1 << ( 7 - ( nX & 7 ) ) );
    1229             :                             }
    1230             :                         }
    1231             :                     }
    1232             :                     else
    1233             :                     {
    1234           0 :                         for( nY = 0L; nY < nHeight; nY++ )
    1235             :                         {
    1236           0 :                             Scanline pSrc = pReadAcc->GetScanline( nY );
    1237           0 :                             long nShift = 0;
    1238           0 :                             for( nX = 0L, nShift = nShiftInit; nX < nWidth; nX++, nShift ^= 4 )
    1239             :                             {
    1240           0 :                                 if( cTest == ( ( pSrc[ nX >> 1 ] >> nShift ) & 0x0f ) )
    1241           0 :                                     pWriteAcc->SetPixel( nY, nX, aWhite );
    1242             :                                 else
    1243           0 :                                     pWriteAcc->SetPixel( nY, nX, aBlack );
    1244             :                             }
    1245             :                         }
    1246             :                     }
    1247             :                 }
    1248          39 :                 else if( pReadAcc->GetScanlineFormat() == BMP_FORMAT_8BIT_PAL )
    1249             :                 {
    1250             :                     // optimized for 8Bit source palette
    1251          29 :                     const sal_uInt8 cTest = aTest.GetIndex();
    1252             : 
    1253          58 :                     if( pWriteAcc->GetScanlineFormat() == BMP_FORMAT_1BIT_MSB_PAL &&
    1254          29 :                         aWhite.GetIndex() == 1 )
    1255             :                     {
    1256             :                         // optimized for 1Bit-MSB destination palette
    1257         406 :                         for( nY = 0L; nY < nHeight; nY++ )
    1258             :                         {
    1259         377 :                             Scanline pSrc = pReadAcc->GetScanline( nY );
    1260         377 :                             Scanline pDst = pWriteAcc->GetScanline( nY );
    1261       40937 :                             for( nX = 0L; nX < nWidth; nX++ )
    1262             :                             {
    1263       40560 :                                 if( cTest == pSrc[ nX ] )
    1264        6156 :                                     pDst[ nX >> 3 ] |= 1 << ( 7 - ( nX & 7 ) );
    1265             :                                 else
    1266       34404 :                                     pDst[ nX >> 3 ] &= ~( 1 << ( 7 - ( nX & 7 ) ) );
    1267             :                             }
    1268             :                         }
    1269             :                     }
    1270             :                     else
    1271             :                     {
    1272           0 :                         for( nY = 0L; nY < nHeight; nY++ )
    1273             :                         {
    1274           0 :                             Scanline pSrc = pReadAcc->GetScanline( nY );
    1275           0 :                             for( nX = 0L; nX < nWidth; nX++ )
    1276             :                             {
    1277           0 :                                 if( cTest == pSrc[ nX ] )
    1278           0 :                                     pWriteAcc->SetPixel( nY, nX, aWhite );
    1279             :                                 else
    1280           0 :                                     pWriteAcc->SetPixel( nY, nX, aBlack );
    1281             :                             }
    1282             :                         }
    1283             :                     }
    1284             :                 }
    1285             :                 else
    1286             :                 {
    1287             :                     // not optimized
    1288         330 :                     for( nY = 0L; nY < nHeight; nY++ )
    1289             :                     {
    1290       11140 :                         for( nX = 0L; nX < nWidth; nX++ )
    1291             :                         {
    1292       10820 :                             if( aTest == pReadAcc->GetPixel( nY, nX ) )
    1293        4338 :                                 pWriteAcc->SetPixel( nY, nX, aWhite );
    1294             :                             else
    1295        6482 :                                 pWriteAcc->SetPixel( nY, nX, aBlack );
    1296             :                         }
    1297             :                     }
    1298          45 :                 }
    1299             :             }
    1300             :             else
    1301             :             {
    1302           4 :                 BitmapColor aCol;
    1303             :                 long        nR, nG, nB;
    1304           4 :                 const long  nMinR = MinMax( (long) rTransColor.GetRed() - nTol, 0, 255 );
    1305           4 :                 const long  nMaxR = MinMax( (long) rTransColor.GetRed() + nTol, 0, 255 );
    1306           4 :                 const long  nMinG = MinMax( (long) rTransColor.GetGreen() - nTol, 0, 255 );
    1307           4 :                 const long  nMaxG = MinMax( (long) rTransColor.GetGreen() + nTol, 0, 255 );
    1308           4 :                 const long  nMinB = MinMax( (long) rTransColor.GetBlue() - nTol, 0, 255 );
    1309           4 :                 const long  nMaxB = MinMax( (long) rTransColor.GetBlue() + nTol, 0, 255 );
    1310             : 
    1311           4 :                 if( pReadAcc->HasPalette() )
    1312             :                 {
    1313           0 :                     for( long nY = 0L; nY < nHeight; nY++ )
    1314             :                     {
    1315           0 :                         for( long nX = 0L; nX < nWidth; nX++ )
    1316             :                         {
    1317           0 :                             aCol = pReadAcc->GetPaletteColor( pReadAcc->GetPixelIndex( nY, nX ) );
    1318           0 :                             nR = aCol.GetRed();
    1319           0 :                             nG = aCol.GetGreen();
    1320           0 :                             nB = aCol.GetBlue();
    1321             : 
    1322           0 :                             if( nMinR <= nR && nMaxR >= nR &&
    1323           0 :                                 nMinG <= nG && nMaxG >= nG &&
    1324           0 :                                 nMinB <= nB && nMaxB >= nB )
    1325             :                             {
    1326           0 :                                 pWriteAcc->SetPixel( nY, nX, aWhite );
    1327             :                             }
    1328             :                             else
    1329           0 :                                 pWriteAcc->SetPixel( nY, nX, aBlack );
    1330             :                         }
    1331             :                     }
    1332             :                 }
    1333             :                 else
    1334             :                 {
    1335          68 :                     for( long nY = 0L; nY < nHeight; nY++ )
    1336             :                     {
    1337        4864 :                         for( long nX = 0L; nX < nWidth; nX++ )
    1338             :                         {
    1339        4800 :                             aCol = pReadAcc->GetPixel( nY, nX );
    1340        4800 :                             nR = aCol.GetRed();
    1341        4800 :                             nG = aCol.GetGreen();
    1342        4800 :                             nB = aCol.GetBlue();
    1343             : 
    1344        4800 :                             if( nMinR <= nR && nMaxR >= nR &&
    1345        3908 :                                 nMinG <= nG && nMaxG >= nG &&
    1346        3784 :                                 nMinB <= nB && nMaxB >= nB )
    1347             :                             {
    1348        3784 :                                 pWriteAcc->SetPixel( nY, nX, aWhite );
    1349             :                             }
    1350             :                             else
    1351        1016 :                                 pWriteAcc->SetPixel( nY, nX, aBlack );
    1352             :                         }
    1353             :                     }
    1354           4 :                 }
    1355             :             }
    1356             : 
    1357          49 :             ReleaseAccess( pReadAcc );
    1358          98 :             bRet = true;
    1359             :         }
    1360             : 
    1361          49 :         ReleaseAccess( pWriteAcc );
    1362             :     }
    1363             : 
    1364          49 :     if( bRet )
    1365             :     {
    1366          49 :         aNewBmp.maPrefSize = maPrefSize;
    1367          49 :         aNewBmp.maPrefMapMode = maPrefMapMode;
    1368             :     }
    1369             :     else
    1370           0 :         aNewBmp = Bitmap();
    1371             : 
    1372          49 :     return aNewBmp;
    1373             : }
    1374             : 
    1375           0 : vcl::Region Bitmap::CreateRegion( const Color& rColor, const Rectangle& rRect ) const
    1376             : {
    1377           0 :     vcl::Region              aRegion;
    1378           0 :     Rectangle           aRect( rRect );
    1379           0 :     BitmapReadAccess*   pReadAcc = const_cast<Bitmap*>(this)->AcquireReadAccess();
    1380             : 
    1381           0 :     aRect.Intersection( Rectangle( Point(), GetSizePixel() ) );
    1382           0 :     aRect.Justify();
    1383             : 
    1384           0 :     if( pReadAcc )
    1385             :     {
    1386             :         //Rectangle         aSubRect;
    1387           0 :         const long          nLeft = aRect.Left();
    1388           0 :         const long          nTop = aRect.Top();
    1389           0 :         const long          nRight = aRect.Right();
    1390           0 :         const long          nBottom = aRect.Bottom();
    1391           0 :         const BitmapColor   aMatch( pReadAcc->GetBestMatchingColor( rColor ) );
    1392             : 
    1393             :         //RectangleVector aRectangles;
    1394             :         //aRegion.ImplBeginAddRect();
    1395           0 :         std::vector< long > aLine;
    1396           0 :         long nYStart(nTop);
    1397           0 :         long nY(nTop);
    1398             : 
    1399           0 :         for( ; nY <= nBottom; nY++ )
    1400             :         {
    1401             :             //aSubRect.Top() = aSubRect.Bottom() = nY;
    1402           0 :             std::vector< long > aNewLine;
    1403           0 :             long nX(nLeft);
    1404             : 
    1405           0 :             for( ; nX <= nRight; )
    1406             :             {
    1407           0 :                 while( ( nX <= nRight ) && ( aMatch != pReadAcc->GetPixel( nY, nX ) ) )
    1408           0 :                     nX++;
    1409             : 
    1410           0 :                 if( nX <= nRight )
    1411             :                 {
    1412           0 :                     aNewLine.push_back(nX);
    1413             :                     //aSubRect.Left() = nX;
    1414             : 
    1415           0 :                     while( ( nX <= nRight ) && ( aMatch == pReadAcc->GetPixel( nY, nX ) ) )
    1416           0 :                         nX++;
    1417             : 
    1418             :                     //aSubRect.Right() = nX - 1L;
    1419           0 :                     aNewLine.push_back(nX - 1);
    1420             : 
    1421             :                     //aRegion.ImplAddRect( aSubRect );
    1422             :                     //aRectangles.push_back(aSubRect);
    1423             :                     //aRegion.Union(aSubRect);
    1424             :                 }
    1425             :             }
    1426             : 
    1427           0 :             if(aNewLine != aLine)
    1428             :             {
    1429             :                 // need to write aLine, it's different from the next line
    1430           0 :                 if(aLine.size())
    1431             :                 {
    1432           0 :                     Rectangle aSubRect;
    1433             : 
    1434             :                     // enter y values and proceed ystart
    1435           0 :                     aSubRect.Top() = nYStart;
    1436           0 :                     aSubRect.Bottom() = nY ? nY - 1 : 0;
    1437             : 
    1438           0 :                     for(size_t a(0); a < aLine.size();)
    1439             :                     {
    1440           0 :                         aSubRect.Left() = aLine[a++];
    1441           0 :                         aSubRect.Right() = aLine[a++];
    1442           0 :                         aRegion.Union(aSubRect);
    1443             :                     }
    1444             :                 }
    1445             : 
    1446             :                 // copy line as new line
    1447           0 :                 aLine = aNewLine;
    1448           0 :                 nYStart = nY;
    1449             :             }
    1450           0 :         }
    1451             : 
    1452             :         // write last line if used
    1453           0 :         if(aLine.size())
    1454             :         {
    1455           0 :             Rectangle aSubRect;
    1456             : 
    1457             :             // enter y values
    1458           0 :             aSubRect.Top() = nYStart;
    1459           0 :             aSubRect.Bottom() = nY ? nY - 1 : 0;
    1460             : 
    1461           0 :             for(size_t a(0); a < aLine.size();)
    1462             :             {
    1463           0 :                 aSubRect.Left() = aLine[a++];
    1464           0 :                 aSubRect.Right() = aLine[a++];
    1465           0 :                 aRegion.Union(aSubRect);
    1466             :             }
    1467             :         }
    1468             : 
    1469             :         //aRegion.ImplEndAddRect();
    1470             :         //aRegion.SetRegionRectangles(aRectangles);
    1471             : 
    1472           0 :         ReleaseAccess( pReadAcc );
    1473             :     }
    1474             :     else
    1475           0 :         aRegion = aRect;
    1476             : 
    1477           0 :     return aRegion;
    1478             : }
    1479             : 
    1480          16 : bool Bitmap::Replace( const Bitmap& rMask, const Color& rReplaceColor )
    1481             : {
    1482          16 :     BitmapReadAccess*   pMaskAcc = ( (Bitmap&) rMask ).AcquireReadAccess();
    1483          16 :     BitmapWriteAccess*  pAcc = AcquireWriteAccess();
    1484          16 :     bool                bRet = false;
    1485             : 
    1486          16 :     if( pMaskAcc && pAcc )
    1487             :     {
    1488          16 :         const long          nWidth = std::min( pMaskAcc->Width(), pAcc->Width() );
    1489          16 :         const long          nHeight = std::min( pMaskAcc->Height(), pAcc->Height() );
    1490          16 :         const BitmapColor   aMaskWhite( pMaskAcc->GetBestMatchingColor( Color( COL_WHITE ) ) );
    1491          32 :         BitmapColor         aReplace;
    1492             : 
    1493          16 :         if( pAcc->HasPalette() )
    1494             :         {
    1495           4 :             const sal_uInt16 nActColors = pAcc->GetPaletteEntryCount();
    1496           4 :             const sal_uInt16 nMaxColors = 1 << pAcc->GetBitCount();
    1497             : 
    1498             :             // default to the nearest color
    1499           4 :             aReplace = pAcc->GetBestMatchingColor( rReplaceColor );
    1500             : 
    1501             :             // for paletted images without a matching palette entry
    1502             :             // look for an unused palette entry (NOTE: expensive!)
    1503           4 :             if( pAcc->GetPaletteColor( aReplace.GetIndex() ) != BitmapColor( rReplaceColor ) )
    1504             :             {
    1505             :                 // if the palette has empty entries use the last one
    1506           0 :                 if( nActColors < nMaxColors )
    1507             :                 {
    1508           0 :                     pAcc->SetPaletteEntryCount( nActColors + 1 );
    1509           0 :                     pAcc->SetPaletteColor( nActColors, rReplaceColor );
    1510           0 :                     aReplace = BitmapColor( (sal_uInt8) nActColors );
    1511             :                 }
    1512             :                 else
    1513             :                 {
    1514           0 :                     boost::scoped_array<bool> pFlags(new bool[ nMaxColors ]);
    1515             : 
    1516             :                     // Set all entries to false
    1517           0 :                     std::fill( pFlags.get(), pFlags.get()+nMaxColors, false );
    1518             : 
    1519           0 :                     for( long nY = 0L; nY < nHeight; nY++ )
    1520           0 :                         for( long nX = 0L; nX < nWidth; nX++ )
    1521           0 :                             pFlags[ pAcc->GetPixelIndex( nY, nX ) ] = true;
    1522             : 
    1523           0 :                     for( sal_uInt16 i = 0UL; i < nMaxColors; i++ )
    1524             :                     {
    1525             :                         // Hurray, we do have an unsused entry
    1526           0 :                         if( !pFlags[ i ] )
    1527             :                         {
    1528           0 :                             pAcc->SetPaletteColor( (sal_uInt16) i, rReplaceColor );
    1529           0 :                             aReplace = BitmapColor( (sal_uInt8) i );
    1530             :                         }
    1531           0 :                     }
    1532             :                 }
    1533             :             }
    1534             :         }
    1535             :         else
    1536          12 :             aReplace = rReplaceColor;
    1537             : 
    1538        1852 :         for( long nY = 0L; nY < nHeight; nY++ )
    1539     1452270 :             for( long nX = 0L; nX < nWidth; nX++ )
    1540     1450434 :                 if( pMaskAcc->GetPixel( nY, nX ) == aMaskWhite )
    1541       13219 :                     pAcc->SetPixel( nY, nX, aReplace );
    1542             : 
    1543          32 :         bRet = true;
    1544             :     }
    1545             : 
    1546          16 :     ReleaseAccess( pMaskAcc );
    1547          16 :     ReleaseAccess( pAcc );
    1548             : 
    1549          16 :     return bRet;
    1550             : }
    1551             : 
    1552           1 : bool Bitmap::Replace( const AlphaMask& rAlpha, const Color& rMergeColor )
    1553             : {
    1554           1 :     Bitmap              aNewBmp( GetSizePixel(), 24 );
    1555           1 :     BitmapReadAccess*   pAcc = AcquireReadAccess();
    1556           1 :     BitmapReadAccess*   pAlphaAcc = ( (AlphaMask&) rAlpha ).AcquireReadAccess();
    1557           1 :     BitmapWriteAccess*  pNewAcc = aNewBmp.AcquireWriteAccess();
    1558           1 :     bool                bRet = false;
    1559             : 
    1560           1 :     if( pAcc && pAlphaAcc && pNewAcc )
    1561             :     {
    1562           1 :         BitmapColor aCol;
    1563           1 :         const long  nWidth = std::min( pAlphaAcc->Width(), pAcc->Width() );
    1564           1 :         const long  nHeight = std::min( pAlphaAcc->Height(), pAcc->Height() );
    1565             : 
    1566         182 :         for( long nY = 0L; nY < nHeight; nY++ )
    1567             :         {
    1568       61902 :             for( long nX = 0L; nX < nWidth; nX++ )
    1569             :             {
    1570       61721 :                 aCol = pAcc->GetColor( nY, nX );
    1571       61721 :                 pNewAcc->SetPixel( nY, nX, aCol.Merge( rMergeColor, 255 - pAlphaAcc->GetPixelIndex( nY, nX ) ) );
    1572             :             }
    1573             :         }
    1574             : 
    1575           1 :         bRet = true;
    1576             :     }
    1577             : 
    1578           1 :     ReleaseAccess( pAcc );
    1579           1 :     ReleaseAccess( pAlphaAcc );
    1580           1 :     ReleaseAccess( pNewAcc );
    1581             : 
    1582           1 :     if( bRet )
    1583             :     {
    1584           1 :         const MapMode   aMap( maPrefMapMode );
    1585           1 :         const Size      aSize( maPrefSize );
    1586             : 
    1587           1 :         *this = aNewBmp;
    1588             : 
    1589           1 :         maPrefMapMode = aMap;
    1590           1 :         maPrefSize = aSize;
    1591             :     }
    1592             : 
    1593           1 :     return bRet;
    1594             : }
    1595             : 
    1596         512 : bool Bitmap::Replace( const Color& rSearchColor, const Color& rReplaceColor, sal_uLong nTol )
    1597             : {
    1598         512 :     if( mpImpBmp )
    1599             :     {
    1600             :         // implementation specific replace
    1601         512 :         ImpBitmap* pImpBmp = new ImpBitmap;
    1602             : 
    1603         512 :         if( pImpBmp->ImplCreate( *mpImpBmp ) && pImpBmp->ImplReplace( rSearchColor, rReplaceColor, nTol ) )
    1604             :         {
    1605           0 :             ImplSetImpBitmap( pImpBmp );
    1606           0 :             maPrefMapMode = MapMode( MAP_PIXEL );
    1607           0 :             maPrefSize = pImpBmp->ImplGetSize();
    1608           0 :             return true;
    1609             :         }
    1610             :         else
    1611             :         {
    1612         512 :             delete pImpBmp;
    1613             :         }
    1614             :     }
    1615             : 
    1616             :     // Bitmaps with 1 bit color depth can cause problems
    1617             :     // if they have other entries than black/white in their palette
    1618         512 :     if( 1 == GetBitCount() )
    1619           0 :         Convert( BMP_CONVERSION_4BIT_COLORS );
    1620             : 
    1621         512 :     BitmapWriteAccess*  pAcc = AcquireWriteAccess();
    1622         512 :     bool                bRet = false;
    1623             : 
    1624         512 :     if( pAcc )
    1625             :     {
    1626         512 :         const long  nMinR = MinMax( (long) rSearchColor.GetRed() - nTol, 0, 255 );
    1627         512 :         const long  nMaxR = MinMax( (long) rSearchColor.GetRed() + nTol, 0, 255 );
    1628         512 :         const long  nMinG = MinMax( (long) rSearchColor.GetGreen() - nTol, 0, 255 );
    1629         512 :         const long  nMaxG = MinMax( (long) rSearchColor.GetGreen() + nTol, 0, 255 );
    1630         512 :         const long  nMinB = MinMax( (long) rSearchColor.GetBlue() - nTol, 0, 255 );
    1631         512 :         const long  nMaxB = MinMax( (long) rSearchColor.GetBlue() + nTol, 0, 255 );
    1632             : 
    1633         512 :         if( pAcc->HasPalette() )
    1634             :         {
    1635           0 :             for( sal_uInt16 i = 0, nPalCount = pAcc->GetPaletteEntryCount(); i < nPalCount; i++ )
    1636             :             {
    1637           0 :                 const BitmapColor& rCol = pAcc->GetPaletteColor( i );
    1638             : 
    1639           0 :                 if( nMinR <= rCol.GetRed() && nMaxR >= rCol.GetRed() &&
    1640           0 :                     nMinG <= rCol.GetGreen() && nMaxG >= rCol.GetGreen() &&
    1641           0 :                     nMinB <= rCol.GetBlue() && nMaxB >= rCol.GetBlue() )
    1642             :                 {
    1643           0 :                     pAcc->SetPaletteColor( i, rReplaceColor );
    1644             :                 }
    1645             :             }
    1646             :         }
    1647             :         else
    1648             :         {
    1649         512 :             BitmapColor         aCol;
    1650        1024 :             const BitmapColor   aReplace( pAcc->GetBestMatchingColor( rReplaceColor ) );
    1651             : 
    1652       12160 :             for( long nY = 0L, nHeight = pAcc->Height(); nY < nHeight; nY++ )
    1653             :             {
    1654      179840 :                 for( long nX = 0L, nWidth = pAcc->Width(); nX < nWidth; nX++ )
    1655             :                 {
    1656      168192 :                     aCol = pAcc->GetPixel( nY, nX );
    1657             : 
    1658      451584 :                     if( nMinR <= aCol.GetRed() && nMaxR >= aCol.GetRed() &&
    1659      172800 :                         nMinG <= aCol.GetGreen() && nMaxG >= aCol.GetGreen() &&
    1660      283392 :                         nMinB <= aCol.GetBlue() && nMaxB >= aCol.GetBlue() )
    1661             :                     {
    1662       57600 :                         pAcc->SetPixel( nY, nX, aReplace );
    1663             :                     }
    1664             :                 }
    1665         512 :             }
    1666             :         }
    1667             : 
    1668         512 :         ReleaseAccess( pAcc );
    1669         512 :         bRet = true;
    1670             :     }
    1671             : 
    1672         512 :     return bRet;
    1673             : }
    1674             : 
    1675          35 : bool Bitmap::Replace( const Color* pSearchColors, const Color* pReplaceColors,
    1676             :                       sal_uLong nColorCount, sal_uLong* _pTols )
    1677             : {
    1678             :     // Bitmaps with 1 bit color depth can cause problems
    1679             :     // if they have other entries than black/white in their palette
    1680          35 :     if( 1 == GetBitCount() )
    1681           0 :         Convert( BMP_CONVERSION_4BIT_COLORS );
    1682             : 
    1683          35 :     BitmapWriteAccess*  pAcc = AcquireWriteAccess();
    1684          35 :     bool                bRet = false;
    1685             : 
    1686          35 :     if( pAcc )
    1687             :     {
    1688          35 :         boost::scoped_array<long> pMinR(new long[ nColorCount ]);
    1689          70 :         boost::scoped_array<long> pMaxR(new long[ nColorCount ]);
    1690          70 :         boost::scoped_array<long> pMinG(new long[ nColorCount ]);
    1691          70 :         boost::scoped_array<long> pMaxG(new long[ nColorCount ]);
    1692          70 :         boost::scoped_array<long> pMinB(new long[ nColorCount ]);
    1693          70 :         boost::scoped_array<long> pMaxB(new long[ nColorCount ]);
    1694             :         long*   pTols;
    1695             :         sal_uLong   i;
    1696             : 
    1697          35 :         if( !_pTols )
    1698             :         {
    1699          35 :             pTols = new long[ nColorCount ];
    1700          35 :             memset( pTols, 0, nColorCount * sizeof( long ) );
    1701             :         }
    1702             :         else
    1703           0 :             pTols = reinterpret_cast<long*>(_pTols);
    1704             : 
    1705         245 :         for( i = 0UL; i < nColorCount; i++ )
    1706             :         {
    1707         210 :             const Color&    rCol = pSearchColors[ i ];
    1708         210 :             const long      nTol = pTols[ i ];
    1709             : 
    1710         210 :             pMinR[ i ] = MinMax( (long) rCol.GetRed() - nTol, 0, 255 );
    1711         210 :             pMaxR[ i ] = MinMax( (long) rCol.GetRed() + nTol, 0, 255 );
    1712         210 :             pMinG[ i ] = MinMax( (long) rCol.GetGreen() - nTol, 0, 255 );
    1713         210 :             pMaxG[ i ] = MinMax( (long) rCol.GetGreen() + nTol, 0, 255 );
    1714         210 :             pMinB[ i ] = MinMax( (long) rCol.GetBlue() - nTol, 0, 255 );
    1715         210 :             pMaxB[ i ] = MinMax( (long) rCol.GetBlue() + nTol, 0, 255 );
    1716             :         }
    1717             : 
    1718          35 :         if( pAcc->HasPalette() )
    1719             :         {
    1720        7555 :             for( sal_uInt16 nEntry = 0, nPalCount = pAcc->GetPaletteEntryCount(); nEntry < nPalCount; nEntry++ )
    1721             :             {
    1722        7520 :                 const BitmapColor& rCol = pAcc->GetPaletteColor( nEntry );
    1723             : 
    1724       22933 :                 for( i = 0UL; i < nColorCount; i++ )
    1725             :                 {
    1726       82893 :                     if( pMinR[ i ] <= rCol.GetRed() && pMaxR[ i ] >= rCol.GetRed() &&
    1727       44459 :                         pMinG[ i ] <= rCol.GetGreen() && pMaxG[ i ] >= rCol.GetGreen() &&
    1728       52384 :                         pMinB[ i ] <= rCol.GetBlue() && pMaxB[ i ] >= rCol.GetBlue() )
    1729             :                     {
    1730        7453 :                         pAcc->SetPaletteColor( (sal_uInt16)nEntry, pReplaceColors[ i ] );
    1731        7453 :                         break;
    1732             :                     }
    1733             :                 }
    1734             :             }
    1735             :         }
    1736             :         else
    1737             :         {
    1738           0 :             BitmapColor     aCol;
    1739           0 :             boost::scoped_array<BitmapColor> pReplaces(new BitmapColor[ nColorCount ]);
    1740             : 
    1741           0 :             for( i = 0UL; i < nColorCount; i++ )
    1742           0 :                 pReplaces[ i ] = pAcc->GetBestMatchingColor( pReplaceColors[ i ] );
    1743             : 
    1744           0 :             for( long nY = 0L, nHeight = pAcc->Height(); nY < nHeight; nY++ )
    1745             :             {
    1746           0 :                 for( long nX = 0L, nWidth = pAcc->Width(); nX < nWidth; nX++ )
    1747             :                 {
    1748           0 :                     aCol = pAcc->GetPixel( nY, nX );
    1749             : 
    1750           0 :                     for( i = 0UL; i < nColorCount; i++ )
    1751             :                     {
    1752           0 :                         if( pMinR[ i ] <= aCol.GetRed() && pMaxR[ i ] >= aCol.GetRed() &&
    1753           0 :                             pMinG[ i ] <= aCol.GetGreen() && pMaxG[ i ] >= aCol.GetGreen() &&
    1754           0 :                             pMinB[ i ] <= aCol.GetBlue() && pMaxB[ i ] >= aCol.GetBlue() )
    1755             :                         {
    1756           0 :                             pAcc->SetPixel( nY, nX, pReplaces[ i ] );
    1757           0 :                             break;
    1758             :                         }
    1759             :                     }
    1760             :                 }
    1761           0 :             }
    1762             :         }
    1763             : 
    1764          35 :         if( !_pTols )
    1765          35 :             delete[] pTols;
    1766             : 
    1767          35 :         ReleaseAccess( pAcc );
    1768          70 :         bRet = true;
    1769             :     }
    1770             : 
    1771          35 :     return bRet;
    1772             : }
    1773             : 
    1774           0 : Bitmap Bitmap::CreateDisplayBitmap( OutputDevice* pDisplay )
    1775             : {
    1776           0 :     Bitmap aDispBmp( *this );
    1777             : 
    1778           0 :     SalGraphics* pDispGraphics = pDisplay->GetGraphics();
    1779             : 
    1780           0 :     if( mpImpBmp && pDispGraphics )
    1781             :     {
    1782           0 :         ImpBitmap* pImpDispBmp = new ImpBitmap;
    1783             : 
    1784           0 :         if( pImpDispBmp->ImplCreate( *mpImpBmp, pDispGraphics ) )
    1785           0 :             aDispBmp.ImplSetImpBitmap( pImpDispBmp );
    1786             :         else
    1787           0 :             delete pImpDispBmp;
    1788             :     }
    1789             : 
    1790           0 :     return aDispBmp;
    1791             : }
    1792             : 
    1793           0 : bool Bitmap::CombineSimple( const Bitmap& rMask, BmpCombine eCombine )
    1794             : {
    1795           0 :     BitmapReadAccess*   pMaskAcc = ( (Bitmap&) rMask ).AcquireReadAccess();
    1796           0 :     BitmapWriteAccess*  pAcc = AcquireWriteAccess();
    1797           0 :     bool                bRet = false;
    1798             : 
    1799           0 :     if( pMaskAcc && pAcc )
    1800             :     {
    1801           0 :         const long          nWidth = std::min( pMaskAcc->Width(), pAcc->Width() );
    1802           0 :         const long          nHeight = std::min( pMaskAcc->Height(), pAcc->Height() );
    1803           0 :         const Color         aColBlack( COL_BLACK );
    1804           0 :         BitmapColor         aPixel;
    1805           0 :         BitmapColor         aMaskPixel;
    1806           0 :         const BitmapColor   aWhite( pAcc->GetBestMatchingColor( Color( COL_WHITE ) ) );
    1807           0 :         const BitmapColor   aBlack( pAcc->GetBestMatchingColor( aColBlack ) );
    1808           0 :         const BitmapColor   aMaskBlack( pMaskAcc->GetBestMatchingColor( aColBlack ) );
    1809             : 
    1810           0 :         switch( eCombine )
    1811             :         {
    1812             :             case( BMP_COMBINE_COPY ):
    1813             :             {
    1814           0 :                 for( long nY = 0L; nY < nHeight; nY++ ) for( long nX = 0L; nX < nWidth; nX++ )
    1815             :                 {
    1816           0 :                     if( pMaskAcc->GetPixel( nY, nX ) == aMaskBlack )
    1817           0 :                         pAcc->SetPixel( nY, nX, aBlack );
    1818             :                     else
    1819           0 :                         pAcc->SetPixel( nY, nX, aWhite );
    1820             :                 }
    1821             :             }
    1822           0 :             break;
    1823             : 
    1824             :             case( BMP_COMBINE_INVERT ):
    1825             :             {
    1826           0 :                 for( long nY = 0L; nY < nHeight; nY++ ) for( long nX = 0L; nX < nWidth; nX++ )
    1827             :                 {
    1828           0 :                     if( pAcc->GetPixel( nY, nX ) == aBlack )
    1829           0 :                         pAcc->SetPixel( nY, nX, aWhite );
    1830             :                     else
    1831           0 :                         pAcc->SetPixel( nY, nX, aBlack );
    1832             :                 }
    1833             :             }
    1834           0 :             break;
    1835             : 
    1836             :             case( BMP_COMBINE_AND ):
    1837             :             {
    1838           0 :                 for( long nY = 0L; nY < nHeight; nY++ ) for( long nX = 0L; nX < nWidth; nX++ )
    1839             :                 {
    1840           0 :                     if( pMaskAcc->GetPixel( nY, nX ) != aMaskBlack && pAcc->GetPixel( nY, nX ) != aBlack )
    1841           0 :                         pAcc->SetPixel( nY, nX, aWhite );
    1842             :                     else
    1843           0 :                         pAcc->SetPixel( nY, nX, aBlack );
    1844             :                 }
    1845             :             }
    1846           0 :             break;
    1847             : 
    1848             :             case( BMP_COMBINE_NAND ):
    1849             :             {
    1850           0 :                 for( long nY = 0L; nY < nHeight; nY++ ) for( long nX = 0L; nX < nWidth; nX++ )
    1851             :                 {
    1852           0 :                     if( pMaskAcc->GetPixel( nY, nX ) != aMaskBlack && pAcc->GetPixel( nY, nX ) != aBlack )
    1853           0 :                         pAcc->SetPixel( nY, nX, aBlack );
    1854             :                     else
    1855           0 :                         pAcc->SetPixel( nY, nX, aWhite );
    1856             :                 }
    1857             :             }
    1858           0 :             break;
    1859             : 
    1860             :             case( BMP_COMBINE_OR ):
    1861             :             {
    1862           0 :                 for( long nY = 0L; nY < nHeight; nY++ ) for( long nX = 0L; nX < nWidth; nX++ )
    1863             :                 {
    1864           0 :                     if( pMaskAcc->GetPixel( nY, nX ) != aMaskBlack || pAcc->GetPixel( nY, nX ) != aBlack )
    1865           0 :                         pAcc->SetPixel( nY, nX, aWhite );
    1866             :                     else
    1867           0 :                         pAcc->SetPixel( nY, nX, aBlack );
    1868             :                 }
    1869             :             }
    1870           0 :             break;
    1871             : 
    1872             :             case( BMP_COMBINE_NOR ):
    1873             :             {
    1874           0 :                 for( long nY = 0L; nY < nHeight; nY++ ) for( long nX = 0L; nX < nWidth; nX++ )
    1875             :                 {
    1876           0 :                     if( pMaskAcc->GetPixel( nY, nX ) != aMaskBlack || pAcc->GetPixel( nY, nX ) != aBlack )
    1877           0 :                         pAcc->SetPixel( nY, nX, aBlack );
    1878             :                     else
    1879           0 :                         pAcc->SetPixel( nY, nX, aWhite );
    1880             :                 }
    1881             :             }
    1882           0 :             break;
    1883             : 
    1884             :             case( BMP_COMBINE_XOR ):
    1885             :             {
    1886           0 :                 for( long nY = 0L; nY < nHeight; nY++ ) for( long nX = 0L; nX < nWidth; nX++ )
    1887             :                 {
    1888           0 :                     aPixel = pAcc->GetPixel( nY, nX );
    1889           0 :                     aMaskPixel = pMaskAcc->GetPixel( nY, nX );
    1890             : 
    1891           0 :                     if( ( aMaskPixel != aMaskBlack && aPixel == aBlack ) ||
    1892           0 :                         ( aMaskPixel == aMaskBlack && aPixel != aBlack ) )
    1893             :                     {
    1894           0 :                         pAcc->SetPixel( nY, nX, aWhite );
    1895             :                     }
    1896             :                     else
    1897           0 :                         pAcc->SetPixel( nY, nX, aBlack );
    1898             :                 }
    1899             :             }
    1900           0 :             break;
    1901             : 
    1902             :             case( BMP_COMBINE_NXOR ):
    1903             :             {
    1904           0 :                 for( long nY = 0L; nY < nHeight; nY++ ) for( long nX = 0L; nX < nWidth; nX++ )
    1905             :                 {
    1906           0 :                     aPixel = pAcc->GetPixel( nY, nX );
    1907           0 :                     aMaskPixel = pMaskAcc->GetPixel( nY, nX );
    1908             : 
    1909           0 :                     if( ( aMaskPixel != aMaskBlack && aPixel == aBlack ) ||
    1910           0 :                         ( aMaskPixel == aMaskBlack && aPixel != aBlack ) )
    1911             :                     {
    1912           0 :                         pAcc->SetPixel( nY, nX, aBlack );
    1913             :                     }
    1914             :                     else
    1915           0 :                         pAcc->SetPixel( nY, nX, aWhite );
    1916             :                 }
    1917             :             }
    1918           0 :             break;
    1919             :         }
    1920             : 
    1921           0 :         bRet = true;
    1922             :     }
    1923             : 
    1924           0 :     ReleaseAccess( pMaskAcc );
    1925           0 :     ReleaseAccess( pAcc );
    1926             : 
    1927           0 :     return bRet;
    1928             : }
    1929             : 
    1930             : // TODO: Have a look at OutputDevice::ImplDrawAlpha() for some
    1931             : // optimizations. Might even consolidate the code here and there.
    1932           0 : bool Bitmap::Blend( const AlphaMask& rAlpha, const Color& rBackgroundColor )
    1933             : {
    1934             :     // Convert to a truecolor bitmap, if we're a paletted one. There's
    1935             :     // room for tradeoff decision here, maybe later for an overload (or a flag)
    1936           0 :     if( GetBitCount() <= 8 )
    1937           0 :         Convert( BMP_CONVERSION_24BIT );
    1938             : 
    1939           0 :     BitmapReadAccess*   pAlphaAcc = const_cast<AlphaMask&>(rAlpha).AcquireReadAccess();
    1940           0 :     BitmapWriteAccess*  pAcc = AcquireWriteAccess();
    1941           0 :     bool                bRet = false;
    1942             : 
    1943           0 :     if( pAlphaAcc && pAcc )
    1944             :     {
    1945           0 :         const long          nWidth = std::min( pAlphaAcc->Width(), pAcc->Width() );
    1946           0 :         const long          nHeight = std::min( pAlphaAcc->Height(), pAcc->Height() );
    1947             : 
    1948           0 :         for( long nY = 0L; nY < nHeight; ++nY )
    1949           0 :             for( long nX = 0L; nX < nWidth; ++nX )
    1950             :                 pAcc->SetPixel( nY, nX,
    1951             :                                 pAcc->GetPixel( nY, nX ).Merge( rBackgroundColor,
    1952           0 :                                                                 255 - pAlphaAcc->GetPixelIndex( nY, nX ) ) );
    1953             : 
    1954           0 :         bRet = true;
    1955             :     }
    1956             : 
    1957           0 :     ReleaseAccess( pAlphaAcc );
    1958           0 :     ReleaseAccess( pAcc );
    1959             : 
    1960           0 :     return bRet;
    1961             : }
    1962             : 
    1963           0 : bool Bitmap::MakeMono( sal_uInt8 cThreshold )
    1964             : {
    1965           0 :     return ImplMakeMono( cThreshold );
    1966             : }
    1967             : 
    1968           0 : bool Bitmap::GetSystemData( BitmapSystemData& rData ) const
    1969             : {
    1970           0 :     bool bRet = false;
    1971           0 :     if( mpImpBmp )
    1972             :     {
    1973           0 :         SalBitmap* pSalBitmap = mpImpBmp->ImplGetSalBitmap();
    1974           0 :         if( pSalBitmap )
    1975           0 :             bRet = pSalBitmap->GetSystemData( rData );
    1976             :     }
    1977             : 
    1978           0 :     return bRet;
    1979             : }
    1980             : 
    1981             : /* vim:set shiftwidth=4 softtabstop=4 expandtab: */

Generated by: LCOV version 1.11