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