19f62ea84SAndrew Rist /************************************************************** 2cdf0e10cSrcweir * 39f62ea84SAndrew Rist * Licensed to the Apache Software Foundation (ASF) under one 49f62ea84SAndrew Rist * or more contributor license agreements. See the NOTICE file 59f62ea84SAndrew Rist * distributed with this work for additional information 69f62ea84SAndrew Rist * regarding copyright ownership. The ASF licenses this file 79f62ea84SAndrew Rist * to you under the Apache License, Version 2.0 (the 89f62ea84SAndrew Rist * "License"); you may not use this file except in compliance 99f62ea84SAndrew Rist * with the License. You may obtain a copy of the License at 109f62ea84SAndrew Rist * 119f62ea84SAndrew Rist * http://www.apache.org/licenses/LICENSE-2.0 129f62ea84SAndrew Rist * 139f62ea84SAndrew Rist * Unless required by applicable law or agreed to in writing, 149f62ea84SAndrew Rist * software distributed under the License is distributed on an 159f62ea84SAndrew Rist * "AS IS" BASIS, WITHOUT WARRANTIES OR CONDITIONS OF ANY 169f62ea84SAndrew Rist * KIND, either express or implied. See the License for the 179f62ea84SAndrew Rist * specific language governing permissions and limitations 189f62ea84SAndrew Rist * under the License. 199f62ea84SAndrew Rist * 209f62ea84SAndrew Rist *************************************************************/ 219f62ea84SAndrew Rist 22cdf0e10cSrcweir // MARKER(update_precomp.py): autogen include statement, do not remove 23cdf0e10cSrcweir #include "precompiled_vcl.hxx" 24cdf0e10cSrcweir 25cdf0e10cSrcweir #include <ctype.h> 26cdf0e10cSrcweir #include <rtl/crc.h> 27cdf0e10cSrcweir #include <tools/stream.hxx> 28cdf0e10cSrcweir #include <tools/debug.hxx> 29cdf0e10cSrcweir #include <tools/rc.h> 30cdf0e10cSrcweir #include <vcl/salbtype.hxx> 31cdf0e10cSrcweir #include <vcl/outdev.hxx> 32cdf0e10cSrcweir #include <vcl/alpha.hxx> 33cdf0e10cSrcweir #include <vcl/bitmapex.hxx> 34cdf0e10cSrcweir #include <vcl/pngread.hxx> 35cdf0e10cSrcweir #include <vcl/svapp.hxx> 36cdf0e10cSrcweir #include <vcl/bmpacc.hxx> 3745fd3b9aSArmin Le Grand #include <vcl/dibtools.hxx> 38cdf0e10cSrcweir #include <image.h> 39cdf0e10cSrcweir #include <impimagetree.hxx> 405f27b83cSArmin Le Grand #include <basegfx/matrix/b2dhommatrixtools.hxx> 41cdf0e10cSrcweir 42cdf0e10cSrcweir // ------------ 43cdf0e10cSrcweir // - BitmapEx - 44cdf0e10cSrcweir // ------------ 45cdf0e10cSrcweir 46cdf0e10cSrcweir BitmapEx::BitmapEx() : 47cdf0e10cSrcweir eTransparent( TRANSPARENT_NONE ), 48cdf0e10cSrcweir bAlpha ( sal_False ) 49cdf0e10cSrcweir { 50cdf0e10cSrcweir } 51cdf0e10cSrcweir 52cdf0e10cSrcweir // ------------------------------------------------------------------ 53cdf0e10cSrcweir 54cdf0e10cSrcweir BitmapEx::BitmapEx( const BitmapEx& rBitmapEx ) : 55cdf0e10cSrcweir aBitmap ( rBitmapEx.aBitmap ), 56cdf0e10cSrcweir aMask ( rBitmapEx.aMask ), 57cdf0e10cSrcweir aBitmapSize ( rBitmapEx.aBitmapSize ), 58cdf0e10cSrcweir aTransparentColor ( rBitmapEx.aTransparentColor ), 59cdf0e10cSrcweir eTransparent ( rBitmapEx.eTransparent ), 60cdf0e10cSrcweir bAlpha ( rBitmapEx.bAlpha ) 61cdf0e10cSrcweir { 62cdf0e10cSrcweir } 63cdf0e10cSrcweir 64cdf0e10cSrcweir BitmapEx::BitmapEx( const BitmapEx& rBitmapEx, Point aSrc, Size aSize ) : 65cdf0e10cSrcweir eTransparent( TRANSPARENT_NONE ), 66cdf0e10cSrcweir bAlpha ( sal_False ) 67cdf0e10cSrcweir { 68cdf0e10cSrcweir if( rBitmapEx.IsEmpty() ) 69cdf0e10cSrcweir return; 70cdf0e10cSrcweir 71cdf0e10cSrcweir aBitmap = Bitmap( aSize, rBitmapEx.aBitmap.GetBitCount() ); 72cdf0e10cSrcweir aBitmapSize = aSize; 73cdf0e10cSrcweir if( rBitmapEx.IsAlpha() ) 74cdf0e10cSrcweir { 75cdf0e10cSrcweir bAlpha = sal_True; 76cdf0e10cSrcweir aMask = AlphaMask( aSize ).ImplGetBitmap(); 77cdf0e10cSrcweir } 78cdf0e10cSrcweir else if( rBitmapEx.IsTransparent() ) 79cdf0e10cSrcweir aMask = Bitmap( aSize, rBitmapEx.aMask.GetBitCount() ); 80cdf0e10cSrcweir 81cdf0e10cSrcweir Rectangle aDestRect( Point( 0, 0 ), aSize ); 82cdf0e10cSrcweir Rectangle aSrcRect( aSrc, aSize ); 83cdf0e10cSrcweir CopyPixel( aDestRect, aSrcRect, &rBitmapEx ); 84cdf0e10cSrcweir } 85cdf0e10cSrcweir 86cdf0e10cSrcweir // ------------------------------------------------------------------ 87cdf0e10cSrcweir 88cdf0e10cSrcweir BitmapEx::BitmapEx( const ResId& rResId ) : 89cdf0e10cSrcweir eTransparent( TRANSPARENT_NONE ), 90cdf0e10cSrcweir bAlpha ( sal_False ) 91cdf0e10cSrcweir { 92cdf0e10cSrcweir static ImplImageTreeSingletonRef aImageTree; 93cdf0e10cSrcweir ResMgr* pResMgr = NULL; 94cdf0e10cSrcweir 95cdf0e10cSrcweir ResMgr::GetResourceSkipHeader( rResId.SetRT( RSC_BITMAP ), &pResMgr ); 96cdf0e10cSrcweir pResMgr->ReadLong(); 97cdf0e10cSrcweir pResMgr->ReadLong(); 98cdf0e10cSrcweir 99cdf0e10cSrcweir const String aFileName( pResMgr->ReadString() ); 100cdf0e10cSrcweir ::rtl::OUString aCurrentSymbolsStyle = Application::GetSettings().GetStyleSettings().GetCurrentSymbolsStyleName(); 101cdf0e10cSrcweir 102cdf0e10cSrcweir if( !aImageTree->loadImage( aFileName, aCurrentSymbolsStyle, *this ) ) 103cdf0e10cSrcweir { 104cdf0e10cSrcweir #ifdef DBG_UTIL 105cdf0e10cSrcweir ByteString aErrorStr( "BitmapEx::BitmapEx( const ResId& rResId ): could not load image <" ); 106cdf0e10cSrcweir DBG_ERROR( ( ( aErrorStr += ByteString( aFileName, RTL_TEXTENCODING_ASCII_US ) ) += '>' ).GetBuffer() ); 107cdf0e10cSrcweir #endif 108cdf0e10cSrcweir } 109cdf0e10cSrcweir } 110cdf0e10cSrcweir 111cdf0e10cSrcweir // ------------------------------------------------------------------ 112cdf0e10cSrcweir 113cdf0e10cSrcweir BitmapEx::BitmapEx( const Bitmap& rBmp ) : 114cdf0e10cSrcweir aBitmap ( rBmp ), 115cdf0e10cSrcweir aBitmapSize ( aBitmap.GetSizePixel() ), 116cdf0e10cSrcweir eTransparent( TRANSPARENT_NONE ), 117cdf0e10cSrcweir bAlpha ( sal_False ) 118cdf0e10cSrcweir { 119cdf0e10cSrcweir } 120cdf0e10cSrcweir 121cdf0e10cSrcweir // ------------------------------------------------------------------ 122cdf0e10cSrcweir 123cdf0e10cSrcweir BitmapEx::BitmapEx( const Bitmap& rBmp, const Bitmap& rMask ) : 124cdf0e10cSrcweir aBitmap ( rBmp ), 125cdf0e10cSrcweir aMask ( rMask ), 126cdf0e10cSrcweir aBitmapSize ( aBitmap.GetSizePixel() ), 127cdf0e10cSrcweir eTransparent ( !rMask ? TRANSPARENT_NONE : TRANSPARENT_BITMAP ), 128cdf0e10cSrcweir bAlpha ( sal_False ) 129cdf0e10cSrcweir { 130ba5b0517SArmin Le Grand if(!!aBitmap && !!aMask && aBitmap.GetSizePixel() != aMask.GetSizePixel()) 131479f2b27SArmin Le Grand { 132479f2b27SArmin Le Grand OSL_ENSURE(false, "Mask size differs from Bitmap size, corrected Mask (!)"); 133ba5b0517SArmin Le Grand aMask.Scale(aBitmap.GetSizePixel()); 134479f2b27SArmin Le Grand } 135cdf0e10cSrcweir 136cdf0e10cSrcweir // #105489# Ensure a mask is exactly one bit deep 137cdf0e10cSrcweir if( !!aMask && aMask.GetBitCount() != 1 ) 138cdf0e10cSrcweir { 139cdf0e10cSrcweir OSL_TRACE("BitmapEx: forced mask to monochrome"); 140cdf0e10cSrcweir aMask.ImplMakeMono( 255 ); 141cdf0e10cSrcweir } 142cdf0e10cSrcweir } 143cdf0e10cSrcweir 144cdf0e10cSrcweir // ------------------------------------------------------------------ 145cdf0e10cSrcweir 146cdf0e10cSrcweir BitmapEx::BitmapEx( const Bitmap& rBmp, const AlphaMask& rAlphaMask ) : 147cdf0e10cSrcweir aBitmap ( rBmp ), 148cdf0e10cSrcweir aMask ( rAlphaMask.ImplGetBitmap() ), 149cdf0e10cSrcweir aBitmapSize ( aBitmap.GetSizePixel() ), 150cdf0e10cSrcweir eTransparent ( !rAlphaMask ? TRANSPARENT_NONE : TRANSPARENT_BITMAP ), 151cdf0e10cSrcweir bAlpha ( !rAlphaMask ? sal_False : sal_True ) 152cdf0e10cSrcweir { 153ba5b0517SArmin Le Grand if(!!aBitmap && !!aMask && aBitmap.GetSizePixel() != aMask.GetSizePixel()) 154479f2b27SArmin Le Grand { 155479f2b27SArmin Le Grand OSL_ENSURE(false, "Alpha size differs from Bitmap size, corrected Mask (!)"); 156479f2b27SArmin Le Grand aMask.Scale(rBmp.GetSizePixel()); 157479f2b27SArmin Le Grand } 158cdf0e10cSrcweir 159cdf0e10cSrcweir // #i75531# the workaround below can go when 160cdf0e10cSrcweir // X11SalGraphics::drawAlphaBitmap()'s render acceleration 161cdf0e10cSrcweir // can handle the bitmap depth mismatch directly 162cdf0e10cSrcweir if( aBitmap.GetBitCount() < aMask.GetBitCount() ) 163cdf0e10cSrcweir aBitmap.Convert( BMP_CONVERSION_24BIT ); 164cdf0e10cSrcweir } 165cdf0e10cSrcweir 166cdf0e10cSrcweir // ------------------------------------------------------------------ 167cdf0e10cSrcweir 168cdf0e10cSrcweir BitmapEx::BitmapEx( const Bitmap& rBmp, const Color& rTransparentColor ) : 169cdf0e10cSrcweir aBitmap ( rBmp ), 170cdf0e10cSrcweir aBitmapSize ( aBitmap.GetSizePixel() ), 171cdf0e10cSrcweir aTransparentColor ( rTransparentColor ), 172cdf0e10cSrcweir eTransparent ( TRANSPARENT_BITMAP ), 173cdf0e10cSrcweir bAlpha ( sal_False ) 174cdf0e10cSrcweir { 175cdf0e10cSrcweir aMask = aBitmap.CreateMask( aTransparentColor ); 176cdf0e10cSrcweir 177cdf0e10cSrcweir DBG_ASSERT( rBmp.GetSizePixel() == aMask.GetSizePixel(), 178cdf0e10cSrcweir "BitmapEx::BitmapEx(): size mismatch for bitmap and alpha mask." ); 179cdf0e10cSrcweir } 180cdf0e10cSrcweir 181cdf0e10cSrcweir // ------------------------------------------------------------------ 182cdf0e10cSrcweir 183cdf0e10cSrcweir BitmapEx::~BitmapEx() 184cdf0e10cSrcweir { 185cdf0e10cSrcweir } 186cdf0e10cSrcweir 187cdf0e10cSrcweir // ------------------------------------------------------------------ 188cdf0e10cSrcweir 189cdf0e10cSrcweir // ------------------------------------------------------------------ 190cdf0e10cSrcweir 191cdf0e10cSrcweir BitmapEx& BitmapEx::operator=( const BitmapEx& rBitmapEx ) 192cdf0e10cSrcweir { 193cdf0e10cSrcweir if( &rBitmapEx != this ) 194cdf0e10cSrcweir { 195cdf0e10cSrcweir aBitmap = rBitmapEx.aBitmap; 196cdf0e10cSrcweir aMask = rBitmapEx.aMask; 197cdf0e10cSrcweir aBitmapSize = rBitmapEx.aBitmapSize; 198cdf0e10cSrcweir aTransparentColor = rBitmapEx.aTransparentColor; 199cdf0e10cSrcweir eTransparent = rBitmapEx.eTransparent; 200cdf0e10cSrcweir bAlpha = rBitmapEx.bAlpha; 201cdf0e10cSrcweir } 202cdf0e10cSrcweir 203cdf0e10cSrcweir return *this; 204cdf0e10cSrcweir } 205cdf0e10cSrcweir 206cdf0e10cSrcweir // ------------------------------------------------------------------ 207cdf0e10cSrcweir 208cdf0e10cSrcweir sal_Bool BitmapEx::operator==( const BitmapEx& rBitmapEx ) const 209cdf0e10cSrcweir { 210cdf0e10cSrcweir if( eTransparent != rBitmapEx.eTransparent ) 211cdf0e10cSrcweir return sal_False; 212cdf0e10cSrcweir 213cdf0e10cSrcweir if( aBitmap != rBitmapEx.aBitmap ) 214cdf0e10cSrcweir return sal_False; 215cdf0e10cSrcweir 216cdf0e10cSrcweir if( aBitmapSize != rBitmapEx.aBitmapSize ) 217cdf0e10cSrcweir return sal_False; 218cdf0e10cSrcweir 219cdf0e10cSrcweir if( eTransparent == TRANSPARENT_NONE ) 220cdf0e10cSrcweir return sal_True; 221cdf0e10cSrcweir 222cdf0e10cSrcweir if( eTransparent == TRANSPARENT_COLOR ) 223cdf0e10cSrcweir return aTransparentColor == rBitmapEx.aTransparentColor; 224cdf0e10cSrcweir 225cdf0e10cSrcweir return( ( aMask == rBitmapEx.aMask ) && ( bAlpha == rBitmapEx.bAlpha ) ); 226cdf0e10cSrcweir } 227cdf0e10cSrcweir 228cdf0e10cSrcweir // ------------------------------------------------------------------ 229cdf0e10cSrcweir 230cdf0e10cSrcweir sal_Bool BitmapEx::IsEqual( const BitmapEx& rBmpEx ) const 231cdf0e10cSrcweir { 232cdf0e10cSrcweir return( rBmpEx.eTransparent == eTransparent && 233cdf0e10cSrcweir rBmpEx.bAlpha == bAlpha && 234cdf0e10cSrcweir rBmpEx.aBitmap.IsEqual( aBitmap ) && 235cdf0e10cSrcweir rBmpEx.aMask.IsEqual( aMask ) ); 236cdf0e10cSrcweir } 237cdf0e10cSrcweir 238cdf0e10cSrcweir // ------------------------------------------------------------------ 239cdf0e10cSrcweir 240cdf0e10cSrcweir sal_Bool BitmapEx::IsEmpty() const 241cdf0e10cSrcweir { 242cdf0e10cSrcweir return( aBitmap.IsEmpty() && aMask.IsEmpty() ); 243cdf0e10cSrcweir } 244cdf0e10cSrcweir 245cdf0e10cSrcweir // ------------------------------------------------------------------ 246cdf0e10cSrcweir 247cdf0e10cSrcweir void BitmapEx::SetEmpty() 248cdf0e10cSrcweir { 249cdf0e10cSrcweir aBitmap.SetEmpty(); 250cdf0e10cSrcweir aMask.SetEmpty(); 251cdf0e10cSrcweir eTransparent = TRANSPARENT_NONE; 252cdf0e10cSrcweir bAlpha = sal_False; 253cdf0e10cSrcweir } 254cdf0e10cSrcweir 255cdf0e10cSrcweir // ------------------------------------------------------------------ 256cdf0e10cSrcweir 257cdf0e10cSrcweir void BitmapEx::Clear() 258cdf0e10cSrcweir { 259cdf0e10cSrcweir SetEmpty(); 260cdf0e10cSrcweir } 261cdf0e10cSrcweir 262cdf0e10cSrcweir // ------------------------------------------------------------------ 263cdf0e10cSrcweir 264cdf0e10cSrcweir sal_Bool BitmapEx::IsTransparent() const 265cdf0e10cSrcweir { 266cdf0e10cSrcweir return( eTransparent != TRANSPARENT_NONE ); 267cdf0e10cSrcweir } 268cdf0e10cSrcweir 269cdf0e10cSrcweir // ------------------------------------------------------------------ 270cdf0e10cSrcweir 271cdf0e10cSrcweir sal_Bool BitmapEx::IsAlpha() const 272cdf0e10cSrcweir { 273cdf0e10cSrcweir return( IsTransparent() && bAlpha ); 274cdf0e10cSrcweir } 275cdf0e10cSrcweir 276cdf0e10cSrcweir // ------------------------------------------------------------------ 277cdf0e10cSrcweir 278cdf0e10cSrcweir Bitmap BitmapEx::GetBitmap( const Color* pTransReplaceColor ) const 279cdf0e10cSrcweir { 280cdf0e10cSrcweir Bitmap aRetBmp( aBitmap ); 281cdf0e10cSrcweir 282cdf0e10cSrcweir if( pTransReplaceColor && ( eTransparent != TRANSPARENT_NONE ) ) 283cdf0e10cSrcweir { 284cdf0e10cSrcweir Bitmap aTempMask; 285cdf0e10cSrcweir 286cdf0e10cSrcweir if( eTransparent == TRANSPARENT_COLOR ) 287cdf0e10cSrcweir aTempMask = aBitmap.CreateMask( aTransparentColor ); 288cdf0e10cSrcweir else 289cdf0e10cSrcweir aTempMask = aMask; 290cdf0e10cSrcweir 291cdf0e10cSrcweir if( !IsAlpha() ) 292cdf0e10cSrcweir aRetBmp.Replace( aTempMask, *pTransReplaceColor ); 293cdf0e10cSrcweir else 294cdf0e10cSrcweir aRetBmp.Replace( GetAlpha(), *pTransReplaceColor ); 295cdf0e10cSrcweir } 296cdf0e10cSrcweir 297cdf0e10cSrcweir return aRetBmp; 298cdf0e10cSrcweir } 299cdf0e10cSrcweir 300cdf0e10cSrcweir // ------------------------------------------------------------------ 301cdf0e10cSrcweir 302cdf0e10cSrcweir BitmapEx BitmapEx::GetColorTransformedBitmapEx( BmpColorMode eColorMode ) const 303cdf0e10cSrcweir { 304cdf0e10cSrcweir BitmapEx aRet; 305cdf0e10cSrcweir 306cdf0e10cSrcweir if( BMP_COLOR_HIGHCONTRAST == eColorMode ) 307cdf0e10cSrcweir { 308cdf0e10cSrcweir aRet = *this; 309cdf0e10cSrcweir aRet.aBitmap = aBitmap.GetColorTransformedBitmap( eColorMode ); 310cdf0e10cSrcweir } 311cdf0e10cSrcweir else if( BMP_COLOR_MONOCHROME_BLACK == eColorMode || 312cdf0e10cSrcweir BMP_COLOR_MONOCHROME_WHITE == eColorMode ) 313cdf0e10cSrcweir { 314cdf0e10cSrcweir aRet = *this; 315cdf0e10cSrcweir aRet.aBitmap = aRet.aBitmap.GetColorTransformedBitmap( eColorMode ); 316cdf0e10cSrcweir 317cdf0e10cSrcweir if( !aRet.aMask.IsEmpty() ) 318cdf0e10cSrcweir { 319cdf0e10cSrcweir aRet.aMask.CombineSimple( aRet.aBitmap, BMP_COMBINE_OR ); 320cdf0e10cSrcweir aRet.aBitmap.Erase( ( BMP_COLOR_MONOCHROME_BLACK == eColorMode ) ? COL_BLACK : COL_WHITE ); 321cdf0e10cSrcweir 322cdf0e10cSrcweir DBG_ASSERT( aRet.aBitmap.GetSizePixel() == aRet.aMask.GetSizePixel(), 323cdf0e10cSrcweir "BitmapEx::GetColorTransformedBitmapEx(): size mismatch for bitmap and alpha mask." ); 324cdf0e10cSrcweir } 325cdf0e10cSrcweir } 326cdf0e10cSrcweir 327cdf0e10cSrcweir return aRet; 328cdf0e10cSrcweir } 329cdf0e10cSrcweir 330cdf0e10cSrcweir // ------------------------------------------------------------------ 331cdf0e10cSrcweir 332cdf0e10cSrcweir Bitmap BitmapEx::GetMask() const 333cdf0e10cSrcweir { 334cdf0e10cSrcweir Bitmap aRet( aMask ); 335cdf0e10cSrcweir 336cdf0e10cSrcweir if( IsAlpha() ) 337cdf0e10cSrcweir aRet.ImplMakeMono( 255 ); 338cdf0e10cSrcweir 339cdf0e10cSrcweir return aRet; 340cdf0e10cSrcweir } 341cdf0e10cSrcweir 342cdf0e10cSrcweir // ------------------------------------------------------------------ 343cdf0e10cSrcweir 344cdf0e10cSrcweir AlphaMask BitmapEx::GetAlpha() const 345cdf0e10cSrcweir { 346cdf0e10cSrcweir AlphaMask aAlpha; 347cdf0e10cSrcweir 348cdf0e10cSrcweir if( IsAlpha() ) 349cdf0e10cSrcweir aAlpha.ImplSetBitmap( aMask ); 350cdf0e10cSrcweir else 351cdf0e10cSrcweir aAlpha = aMask; 352cdf0e10cSrcweir 353cdf0e10cSrcweir return aAlpha; 354cdf0e10cSrcweir } 355cdf0e10cSrcweir 356cdf0e10cSrcweir // ------------------------------------------------------------------ 357cdf0e10cSrcweir 358cdf0e10cSrcweir sal_uLong BitmapEx::GetSizeBytes() const 359cdf0e10cSrcweir { 360cdf0e10cSrcweir sal_uLong nSizeBytes = aBitmap.GetSizeBytes(); 361cdf0e10cSrcweir 362cdf0e10cSrcweir if( eTransparent == TRANSPARENT_BITMAP ) 363cdf0e10cSrcweir nSizeBytes += aMask.GetSizeBytes(); 364cdf0e10cSrcweir 365cdf0e10cSrcweir return nSizeBytes; 366cdf0e10cSrcweir } 367cdf0e10cSrcweir 368cdf0e10cSrcweir // ------------------------------------------------------------------ 369cdf0e10cSrcweir 370cdf0e10cSrcweir sal_uLong BitmapEx::GetChecksum() const 371cdf0e10cSrcweir { 372cdf0e10cSrcweir sal_uInt32 nCrc = aBitmap.GetChecksum(); 373cdf0e10cSrcweir SVBT32 aBT32; 374cdf0e10cSrcweir 375cdf0e10cSrcweir UInt32ToSVBT32( (long) eTransparent, aBT32 ); 376cdf0e10cSrcweir nCrc = rtl_crc32( nCrc, aBT32, 4 ); 377cdf0e10cSrcweir 378cdf0e10cSrcweir UInt32ToSVBT32( (long) bAlpha, aBT32 ); 379cdf0e10cSrcweir nCrc = rtl_crc32( nCrc, aBT32, 4 ); 380cdf0e10cSrcweir 381cdf0e10cSrcweir if( ( TRANSPARENT_BITMAP == eTransparent ) && !aMask.IsEmpty() ) 382cdf0e10cSrcweir { 383cdf0e10cSrcweir UInt32ToSVBT32( aMask.GetChecksum(), aBT32 ); 384cdf0e10cSrcweir nCrc = rtl_crc32( nCrc, aBT32, 4 ); 385cdf0e10cSrcweir } 386cdf0e10cSrcweir 387cdf0e10cSrcweir return nCrc; 388cdf0e10cSrcweir } 389cdf0e10cSrcweir 390cdf0e10cSrcweir // ------------------------------------------------------------------ 391cdf0e10cSrcweir 39254628ca4SArmin Le Grand void BitmapEx::SetSizePixel( const Size& rNewSize, sal_uInt32 nScaleFlag ) 393cdf0e10cSrcweir { 39454628ca4SArmin Le Grand if(GetSizePixel() != rNewSize) 39554628ca4SArmin Le Grand { 39654628ca4SArmin Le Grand Scale( rNewSize, nScaleFlag ); 39754628ca4SArmin Le Grand } 398cdf0e10cSrcweir } 399cdf0e10cSrcweir 400cdf0e10cSrcweir // ------------------------------------------------------------------ 401cdf0e10cSrcweir 402cdf0e10cSrcweir sal_Bool BitmapEx::Invert() 403cdf0e10cSrcweir { 404cdf0e10cSrcweir sal_Bool bRet = sal_False; 405cdf0e10cSrcweir 406cdf0e10cSrcweir if( !!aBitmap ) 407cdf0e10cSrcweir { 408cdf0e10cSrcweir bRet = aBitmap.Invert(); 409cdf0e10cSrcweir 410cdf0e10cSrcweir if( bRet && ( eTransparent == TRANSPARENT_COLOR ) ) 411cdf0e10cSrcweir aTransparentColor = BitmapColor( aTransparentColor ).Invert(); 412cdf0e10cSrcweir } 413cdf0e10cSrcweir 414cdf0e10cSrcweir return bRet; 415cdf0e10cSrcweir } 416cdf0e10cSrcweir 417cdf0e10cSrcweir // ------------------------------------------------------------------ 418cdf0e10cSrcweir 419cdf0e10cSrcweir sal_Bool BitmapEx::Mirror( sal_uLong nMirrorFlags ) 420cdf0e10cSrcweir { 421cdf0e10cSrcweir sal_Bool bRet = sal_False; 422cdf0e10cSrcweir 423cdf0e10cSrcweir if( !!aBitmap ) 424cdf0e10cSrcweir { 425cdf0e10cSrcweir bRet = aBitmap.Mirror( nMirrorFlags ); 426cdf0e10cSrcweir 427cdf0e10cSrcweir if( bRet && ( eTransparent == TRANSPARENT_BITMAP ) && !!aMask ) 428cdf0e10cSrcweir aMask.Mirror( nMirrorFlags ); 429cdf0e10cSrcweir } 430cdf0e10cSrcweir 431cdf0e10cSrcweir return bRet; 432cdf0e10cSrcweir } 433cdf0e10cSrcweir 434cdf0e10cSrcweir // ------------------------------------------------------------------ 435cdf0e10cSrcweir 43654628ca4SArmin Le Grand sal_Bool BitmapEx::Scale( const double& rScaleX, const double& rScaleY, sal_uInt32 nScaleFlag ) 437cdf0e10cSrcweir { 438cdf0e10cSrcweir sal_Bool bRet = sal_False; 439cdf0e10cSrcweir 440cdf0e10cSrcweir if( !!aBitmap ) 441cdf0e10cSrcweir { 442cdf0e10cSrcweir bRet = aBitmap.Scale( rScaleX, rScaleY, nScaleFlag ); 443cdf0e10cSrcweir 444cdf0e10cSrcweir if( bRet && ( eTransparent == TRANSPARENT_BITMAP ) && !!aMask ) 44537ab0f2dSArmin Le Grand { 44637ab0f2dSArmin Le Grand aMask.Scale( rScaleX, rScaleY, nScaleFlag ); 44737ab0f2dSArmin Le Grand } 448cdf0e10cSrcweir 449cdf0e10cSrcweir aBitmapSize = aBitmap.GetSizePixel(); 450cdf0e10cSrcweir 451cdf0e10cSrcweir DBG_ASSERT( !aMask || aBitmap.GetSizePixel() == aMask.GetSizePixel(), 452cdf0e10cSrcweir "BitmapEx::Scale(): size mismatch for bitmap and alpha mask." ); 453cdf0e10cSrcweir } 454cdf0e10cSrcweir 455cdf0e10cSrcweir return bRet; 456cdf0e10cSrcweir } 457cdf0e10cSrcweir 458cdf0e10cSrcweir // ------------------------------------------------------------------------ 459cdf0e10cSrcweir 46054628ca4SArmin Le Grand sal_Bool BitmapEx::Scale( const Size& rNewSize, sal_uInt32 nScaleFlag ) 461cdf0e10cSrcweir { 462cdf0e10cSrcweir sal_Bool bRet; 463cdf0e10cSrcweir 464cdf0e10cSrcweir if( aBitmapSize.Width() && aBitmapSize.Height() ) 465cdf0e10cSrcweir { 466cdf0e10cSrcweir bRet = Scale( (double) rNewSize.Width() / aBitmapSize.Width(), 467cdf0e10cSrcweir (double) rNewSize.Height() / aBitmapSize.Height(), 468cdf0e10cSrcweir nScaleFlag ); 469cdf0e10cSrcweir } 470cdf0e10cSrcweir else 471cdf0e10cSrcweir bRet = sal_True; 472cdf0e10cSrcweir 473cdf0e10cSrcweir return bRet; 474cdf0e10cSrcweir } 475cdf0e10cSrcweir 476cdf0e10cSrcweir // ------------------------------------------------------------------ 477cdf0e10cSrcweir 478cdf0e10cSrcweir sal_Bool BitmapEx::Rotate( long nAngle10, const Color& rFillColor ) 479cdf0e10cSrcweir { 480cdf0e10cSrcweir sal_Bool bRet = sal_False; 481cdf0e10cSrcweir 482cdf0e10cSrcweir if( !!aBitmap ) 483cdf0e10cSrcweir { 484cdf0e10cSrcweir const sal_Bool bTransRotate = ( Color( COL_TRANSPARENT ) == rFillColor ); 485cdf0e10cSrcweir 486cdf0e10cSrcweir if( bTransRotate ) 487cdf0e10cSrcweir { 488cdf0e10cSrcweir if( eTransparent == TRANSPARENT_COLOR ) 489cdf0e10cSrcweir bRet = aBitmap.Rotate( nAngle10, aTransparentColor ); 490cdf0e10cSrcweir else 491cdf0e10cSrcweir { 492cdf0e10cSrcweir bRet = aBitmap.Rotate( nAngle10, COL_BLACK ); 493cdf0e10cSrcweir 494cdf0e10cSrcweir if( eTransparent == TRANSPARENT_NONE ) 495cdf0e10cSrcweir { 496cdf0e10cSrcweir aMask = Bitmap( aBitmapSize, 1 ); 497cdf0e10cSrcweir aMask.Erase( COL_BLACK ); 498cdf0e10cSrcweir eTransparent = TRANSPARENT_BITMAP; 499cdf0e10cSrcweir } 500cdf0e10cSrcweir 501cdf0e10cSrcweir if( bRet && !!aMask ) 502cdf0e10cSrcweir aMask.Rotate( nAngle10, COL_WHITE ); 503cdf0e10cSrcweir } 504cdf0e10cSrcweir } 505cdf0e10cSrcweir else 506cdf0e10cSrcweir { 507cdf0e10cSrcweir bRet = aBitmap.Rotate( nAngle10, rFillColor ); 508cdf0e10cSrcweir 509cdf0e10cSrcweir if( bRet && ( eTransparent == TRANSPARENT_BITMAP ) && !!aMask ) 510cdf0e10cSrcweir aMask.Rotate( nAngle10, COL_WHITE ); 511cdf0e10cSrcweir } 512cdf0e10cSrcweir 513cdf0e10cSrcweir aBitmapSize = aBitmap.GetSizePixel(); 514cdf0e10cSrcweir 515cdf0e10cSrcweir DBG_ASSERT( !aMask || aBitmap.GetSizePixel() == aMask.GetSizePixel(), 516cdf0e10cSrcweir "BitmapEx::Rotate(): size mismatch for bitmap and alpha mask." ); 517cdf0e10cSrcweir } 518cdf0e10cSrcweir 519cdf0e10cSrcweir return bRet; 520cdf0e10cSrcweir } 521cdf0e10cSrcweir 522cdf0e10cSrcweir // ------------------------------------------------------------------ 523cdf0e10cSrcweir 524cdf0e10cSrcweir sal_Bool BitmapEx::Crop( const Rectangle& rRectPixel ) 525cdf0e10cSrcweir { 526cdf0e10cSrcweir sal_Bool bRet = sal_False; 527cdf0e10cSrcweir 528cdf0e10cSrcweir if( !!aBitmap ) 529cdf0e10cSrcweir { 530cdf0e10cSrcweir bRet = aBitmap.Crop( rRectPixel ); 531cdf0e10cSrcweir 532cdf0e10cSrcweir if( bRet && ( eTransparent == TRANSPARENT_BITMAP ) && !!aMask ) 533cdf0e10cSrcweir aMask.Crop( rRectPixel ); 534cdf0e10cSrcweir 535cdf0e10cSrcweir aBitmapSize = aBitmap.GetSizePixel(); 536cdf0e10cSrcweir 537cdf0e10cSrcweir DBG_ASSERT( !aMask || aBitmap.GetSizePixel() == aMask.GetSizePixel(), 538cdf0e10cSrcweir "BitmapEx::Crop(): size mismatch for bitmap and alpha mask." ); 539cdf0e10cSrcweir } 540cdf0e10cSrcweir 541cdf0e10cSrcweir return bRet; 542cdf0e10cSrcweir } 543cdf0e10cSrcweir 544cdf0e10cSrcweir // ------------------------------------------------------------------ 545cdf0e10cSrcweir 546cdf0e10cSrcweir sal_Bool BitmapEx::Convert( BmpConversion eConversion ) 547cdf0e10cSrcweir { 548cdf0e10cSrcweir return( !!aBitmap ? aBitmap.Convert( eConversion ) : sal_False ); 549cdf0e10cSrcweir } 550cdf0e10cSrcweir 551cdf0e10cSrcweir // ------------------------------------------------------------------ 552cdf0e10cSrcweir 553cdf0e10cSrcweir sal_Bool BitmapEx::ReduceColors( sal_uInt16 nNewColorCount, BmpReduce eReduce ) 554cdf0e10cSrcweir { 555cdf0e10cSrcweir return( !!aBitmap ? aBitmap.ReduceColors( nNewColorCount, eReduce ) : sal_False ); 556cdf0e10cSrcweir } 557cdf0e10cSrcweir 558cdf0e10cSrcweir // ------------------------------------------------------------------ 559cdf0e10cSrcweir 560cdf0e10cSrcweir sal_Bool BitmapEx::Expand( sal_uLong nDX, sal_uLong nDY, const Color* pInitColor, sal_Bool bExpandTransparent ) 561cdf0e10cSrcweir { 562cdf0e10cSrcweir sal_Bool bRet = sal_False; 563cdf0e10cSrcweir 564cdf0e10cSrcweir if( !!aBitmap ) 565cdf0e10cSrcweir { 566cdf0e10cSrcweir bRet = aBitmap.Expand( nDX, nDY, pInitColor ); 567cdf0e10cSrcweir 568cdf0e10cSrcweir if( bRet && ( eTransparent == TRANSPARENT_BITMAP ) && !!aMask ) 569cdf0e10cSrcweir { 570cdf0e10cSrcweir Color aColor( bExpandTransparent ? COL_WHITE : COL_BLACK ); 571cdf0e10cSrcweir aMask.Expand( nDX, nDY, &aColor ); 572cdf0e10cSrcweir } 573cdf0e10cSrcweir 574cdf0e10cSrcweir aBitmapSize = aBitmap.GetSizePixel(); 575cdf0e10cSrcweir 576cdf0e10cSrcweir DBG_ASSERT( !aMask || aBitmap.GetSizePixel() == aMask.GetSizePixel(), 577cdf0e10cSrcweir "BitmapEx::Expand(): size mismatch for bitmap and alpha mask." ); 578cdf0e10cSrcweir } 579cdf0e10cSrcweir 580cdf0e10cSrcweir return bRet; 581cdf0e10cSrcweir } 582cdf0e10cSrcweir 583cdf0e10cSrcweir // ------------------------------------------------------------------ 584cdf0e10cSrcweir 585cdf0e10cSrcweir sal_Bool BitmapEx::CopyPixel( const Rectangle& rRectDst, const Rectangle& rRectSrc, 586cdf0e10cSrcweir const BitmapEx* pBmpExSrc ) 587cdf0e10cSrcweir { 588cdf0e10cSrcweir sal_Bool bRet = sal_False; 589cdf0e10cSrcweir 590cdf0e10cSrcweir if( !pBmpExSrc || pBmpExSrc->IsEmpty() ) 591cdf0e10cSrcweir { 592cdf0e10cSrcweir if( !aBitmap.IsEmpty() ) 593cdf0e10cSrcweir { 594cdf0e10cSrcweir bRet = aBitmap.CopyPixel( rRectDst, rRectSrc ); 595cdf0e10cSrcweir 596cdf0e10cSrcweir if( bRet && ( eTransparent == TRANSPARENT_BITMAP ) && !!aMask ) 597cdf0e10cSrcweir aMask.CopyPixel( rRectDst, rRectSrc ); 598cdf0e10cSrcweir } 599cdf0e10cSrcweir } 600cdf0e10cSrcweir else 601cdf0e10cSrcweir { 602cdf0e10cSrcweir if( !aBitmap.IsEmpty() ) 603cdf0e10cSrcweir { 604cdf0e10cSrcweir bRet = aBitmap.CopyPixel( rRectDst, rRectSrc, &pBmpExSrc->aBitmap ); 605cdf0e10cSrcweir 606cdf0e10cSrcweir if( bRet ) 607cdf0e10cSrcweir { 608cdf0e10cSrcweir if( pBmpExSrc->IsAlpha() ) 609cdf0e10cSrcweir { 610cdf0e10cSrcweir if( IsAlpha() ) 611cdf0e10cSrcweir // cast to use the optimized AlphaMask::CopyPixel 612cdf0e10cSrcweir ((AlphaMask*) &aMask)->CopyPixel( rRectDst, rRectSrc, (AlphaMask*)&pBmpExSrc->aMask ); 613cdf0e10cSrcweir else if( IsTransparent() ) 614cdf0e10cSrcweir { 615cdf0e10cSrcweir AlphaMask* pAlpha = new AlphaMask( aMask ); 616cdf0e10cSrcweir 617cdf0e10cSrcweir aMask = pAlpha->ImplGetBitmap(); 618cdf0e10cSrcweir delete pAlpha; 619cdf0e10cSrcweir bAlpha = sal_True; 620cdf0e10cSrcweir aMask.CopyPixel( rRectDst, rRectSrc, &pBmpExSrc->aMask ); 621cdf0e10cSrcweir } 622cdf0e10cSrcweir else 623cdf0e10cSrcweir { 624cdf0e10cSrcweir sal_uInt8 cBlack = 0; 625cdf0e10cSrcweir AlphaMask* pAlpha = new AlphaMask( GetSizePixel(), &cBlack ); 626cdf0e10cSrcweir 627cdf0e10cSrcweir aMask = pAlpha->ImplGetBitmap(); 628cdf0e10cSrcweir delete pAlpha; 629cdf0e10cSrcweir eTransparent = TRANSPARENT_BITMAP; 630cdf0e10cSrcweir bAlpha = sal_True; 631cdf0e10cSrcweir aMask.CopyPixel( rRectDst, rRectSrc, &pBmpExSrc->aMask ); 632cdf0e10cSrcweir } 633cdf0e10cSrcweir } 634cdf0e10cSrcweir else if( pBmpExSrc->IsTransparent() ) 635cdf0e10cSrcweir { 636cdf0e10cSrcweir if( IsAlpha() ) 637cdf0e10cSrcweir { 638cdf0e10cSrcweir AlphaMask aAlpha( pBmpExSrc->aMask ); 639cdf0e10cSrcweir aMask.CopyPixel( rRectDst, rRectSrc, &aAlpha.ImplGetBitmap() ); 640cdf0e10cSrcweir } 641cdf0e10cSrcweir else if( IsTransparent() ) 642cdf0e10cSrcweir aMask.CopyPixel( rRectDst, rRectSrc, &pBmpExSrc->aMask ); 643cdf0e10cSrcweir else 644cdf0e10cSrcweir { 645cdf0e10cSrcweir aMask = Bitmap( GetSizePixel(), 1 ); 646cdf0e10cSrcweir aMask.Erase( Color( COL_BLACK ) ); 647cdf0e10cSrcweir eTransparent = TRANSPARENT_BITMAP; 648cdf0e10cSrcweir aMask.CopyPixel( rRectDst, rRectSrc, &pBmpExSrc->aMask ); 649cdf0e10cSrcweir } 650cdf0e10cSrcweir } 651cdf0e10cSrcweir else if( IsAlpha() ) 652cdf0e10cSrcweir { 653cdf0e10cSrcweir sal_uInt8 cBlack = 0; 654cdf0e10cSrcweir const AlphaMask aAlphaSrc( pBmpExSrc->GetSizePixel(), &cBlack ); 655cdf0e10cSrcweir 656cdf0e10cSrcweir aMask.CopyPixel( rRectDst, rRectSrc, &aAlphaSrc.ImplGetBitmap() ); 657cdf0e10cSrcweir } 658cdf0e10cSrcweir else if( IsTransparent() ) 659cdf0e10cSrcweir { 660cdf0e10cSrcweir Bitmap aMaskSrc( pBmpExSrc->GetSizePixel(), 1 ); 661cdf0e10cSrcweir 662cdf0e10cSrcweir aMaskSrc.Erase( Color( COL_BLACK ) ); 663cdf0e10cSrcweir aMask.CopyPixel( rRectDst, rRectSrc, &aMaskSrc ); 664cdf0e10cSrcweir } 665cdf0e10cSrcweir } 666cdf0e10cSrcweir } 667cdf0e10cSrcweir } 668cdf0e10cSrcweir 669cdf0e10cSrcweir return bRet; 670cdf0e10cSrcweir } 671cdf0e10cSrcweir 672cdf0e10cSrcweir // ------------------------------------------------------------------ 673cdf0e10cSrcweir 674cdf0e10cSrcweir sal_Bool BitmapEx::Erase( const Color& rFillColor ) 675cdf0e10cSrcweir { 676cdf0e10cSrcweir sal_Bool bRet = sal_False; 677cdf0e10cSrcweir 678cdf0e10cSrcweir if( !!aBitmap ) 679cdf0e10cSrcweir { 680cdf0e10cSrcweir bRet = aBitmap.Erase( rFillColor ); 681cdf0e10cSrcweir 682cdf0e10cSrcweir if( bRet && ( eTransparent == TRANSPARENT_BITMAP ) && !!aMask ) 683cdf0e10cSrcweir { 684cdf0e10cSrcweir // #104416# Respect transparency on fill color 685cdf0e10cSrcweir if( rFillColor.GetTransparency() ) 686cdf0e10cSrcweir { 687cdf0e10cSrcweir const Color aFill( rFillColor.GetTransparency(), rFillColor.GetTransparency(), rFillColor.GetTransparency() ); 688cdf0e10cSrcweir aMask.Erase( aFill ); 689cdf0e10cSrcweir } 690cdf0e10cSrcweir else 691cdf0e10cSrcweir { 692cdf0e10cSrcweir const Color aBlack( COL_BLACK ); 693cdf0e10cSrcweir aMask.Erase( aBlack ); 694cdf0e10cSrcweir } 695cdf0e10cSrcweir } 696cdf0e10cSrcweir } 697cdf0e10cSrcweir 698cdf0e10cSrcweir return bRet; 699cdf0e10cSrcweir } 700cdf0e10cSrcweir 701cdf0e10cSrcweir // ------------------------------------------------------------------ 702cdf0e10cSrcweir 703cdf0e10cSrcweir sal_Bool BitmapEx::Dither( sal_uLong nDitherFlags ) 704cdf0e10cSrcweir { 705cdf0e10cSrcweir return( !!aBitmap ? aBitmap.Dither( nDitherFlags ) : sal_False ); 706cdf0e10cSrcweir } 707cdf0e10cSrcweir 708cdf0e10cSrcweir // ------------------------------------------------------------------ 709cdf0e10cSrcweir 710cdf0e10cSrcweir sal_Bool BitmapEx::Replace( const Color& rSearchColor, const Color& rReplaceColor, sal_uLong nTol ) 711cdf0e10cSrcweir { 712cdf0e10cSrcweir return( !!aBitmap ? aBitmap.Replace( rSearchColor, rReplaceColor, nTol ) : sal_False ); 713cdf0e10cSrcweir } 714cdf0e10cSrcweir 715cdf0e10cSrcweir // ------------------------------------------------------------------ 716cdf0e10cSrcweir 717cdf0e10cSrcweir sal_Bool BitmapEx::Replace( const Color* pSearchColors, const Color* pReplaceColors, sal_uLong nColorCount, const sal_uLong* pTols ) 718cdf0e10cSrcweir { 719cdf0e10cSrcweir return( !!aBitmap ? aBitmap.Replace( pSearchColors, pReplaceColors, nColorCount, (sal_uLong*) pTols ) : sal_False ); 720cdf0e10cSrcweir } 721cdf0e10cSrcweir 722cdf0e10cSrcweir // ------------------------------------------------------------------ 723cdf0e10cSrcweir 724cdf0e10cSrcweir sal_Bool BitmapEx::Adjust( short nLuminancePercent, short nContrastPercent, 725cdf0e10cSrcweir short nChannelRPercent, short nChannelGPercent, short nChannelBPercent, 726cdf0e10cSrcweir double fGamma, sal_Bool bInvert ) 727cdf0e10cSrcweir { 728cdf0e10cSrcweir return( !!aBitmap ? aBitmap.Adjust( nLuminancePercent, nContrastPercent, 729cdf0e10cSrcweir nChannelRPercent, nChannelGPercent, nChannelBPercent, 730cdf0e10cSrcweir fGamma, bInvert ) : sal_False ); 731cdf0e10cSrcweir } 732cdf0e10cSrcweir 733cdf0e10cSrcweir // ------------------------------------------------------------------ 734cdf0e10cSrcweir 735cdf0e10cSrcweir sal_Bool BitmapEx::Filter( BmpFilter eFilter, const BmpFilterParam* pFilterParam, const Link* pProgress ) 736cdf0e10cSrcweir { 737cdf0e10cSrcweir return( !!aBitmap ? aBitmap.Filter( eFilter, pFilterParam, pProgress ) : sal_False ); 738cdf0e10cSrcweir } 739cdf0e10cSrcweir 740cdf0e10cSrcweir // ------------------------------------------------------------------ 741cdf0e10cSrcweir 742cdf0e10cSrcweir void BitmapEx::Draw( OutputDevice* pOutDev, const Point& rDestPt ) const 743cdf0e10cSrcweir { 744cdf0e10cSrcweir pOutDev->DrawBitmapEx( rDestPt, *this ); 745cdf0e10cSrcweir } 746cdf0e10cSrcweir 747cdf0e10cSrcweir // ------------------------------------------------------------------ 748cdf0e10cSrcweir 749cdf0e10cSrcweir void BitmapEx::Draw( OutputDevice* pOutDev, 750cdf0e10cSrcweir const Point& rDestPt, const Size& rDestSize ) const 751cdf0e10cSrcweir { 752cdf0e10cSrcweir pOutDev->DrawBitmapEx( rDestPt, rDestSize, *this ); 753cdf0e10cSrcweir } 754cdf0e10cSrcweir 755cdf0e10cSrcweir // ------------------------------------------------------------------ 756cdf0e10cSrcweir 757cdf0e10cSrcweir void BitmapEx::Draw( OutputDevice* pOutDev, 758cdf0e10cSrcweir const Point& rDestPt, const Size& rDestSize, 759cdf0e10cSrcweir const Point& rSrcPtPixel, const Size& rSrcSizePixel ) const 760cdf0e10cSrcweir { 761cdf0e10cSrcweir pOutDev->DrawBitmapEx( rDestPt, rDestSize, rSrcPtPixel, rSrcSizePixel, *this ); 762cdf0e10cSrcweir } 763cdf0e10cSrcweir 764cdf0e10cSrcweir // ------------------------------------------------------------------ 765cdf0e10cSrcweir 766cdf0e10cSrcweir sal_uInt8 BitmapEx::GetTransparency(sal_Int32 nX, sal_Int32 nY) const 767cdf0e10cSrcweir { 768cdf0e10cSrcweir sal_uInt8 nTransparency(0xff); 769cdf0e10cSrcweir 770cdf0e10cSrcweir if(!aBitmap.IsEmpty()) 771cdf0e10cSrcweir { 772cdf0e10cSrcweir if(nX >= 0 && nX < aBitmapSize.Width() && nY >= 0 && nY < aBitmapSize.Height()) 773cdf0e10cSrcweir { 774cdf0e10cSrcweir switch(eTransparent) 775cdf0e10cSrcweir { 776cdf0e10cSrcweir case TRANSPARENT_NONE: 777cdf0e10cSrcweir { 778cdf0e10cSrcweir // not transparent, ergo all covered 779cdf0e10cSrcweir nTransparency = 0x00; 780cdf0e10cSrcweir break; 781cdf0e10cSrcweir } 782cdf0e10cSrcweir case TRANSPARENT_COLOR: 783cdf0e10cSrcweir { 784cdf0e10cSrcweir Bitmap aTestBitmap(aBitmap); 785cdf0e10cSrcweir BitmapReadAccess* pRead = aTestBitmap.AcquireReadAccess(); 786cdf0e10cSrcweir 787cdf0e10cSrcweir if(pRead) 788cdf0e10cSrcweir { 789cdf0e10cSrcweir const Color aColor = pRead->GetColor(nY, nX); 790cdf0e10cSrcweir 791cdf0e10cSrcweir // if color is not equal to TransparentColor, we are not transparent 792cdf0e10cSrcweir if(aColor != aTransparentColor) 793cdf0e10cSrcweir { 794cdf0e10cSrcweir nTransparency = 0x00; 795cdf0e10cSrcweir } 796cdf0e10cSrcweir 797cdf0e10cSrcweir aTestBitmap.ReleaseAccess(pRead); 798cdf0e10cSrcweir } 799cdf0e10cSrcweir break; 800cdf0e10cSrcweir } 801cdf0e10cSrcweir case TRANSPARENT_BITMAP: 802cdf0e10cSrcweir { 803cdf0e10cSrcweir if(!aMask.IsEmpty()) 804cdf0e10cSrcweir { 805cdf0e10cSrcweir Bitmap aTestBitmap(aMask); 806cdf0e10cSrcweir BitmapReadAccess* pRead = aTestBitmap.AcquireReadAccess(); 807cdf0e10cSrcweir 808cdf0e10cSrcweir if(pRead) 809cdf0e10cSrcweir { 810cdf0e10cSrcweir const BitmapColor aBitmapColor(pRead->GetPixel(nY, nX)); 811cdf0e10cSrcweir 812cdf0e10cSrcweir if(bAlpha) 813cdf0e10cSrcweir { 814cdf0e10cSrcweir nTransparency = aBitmapColor.GetIndex(); 815cdf0e10cSrcweir } 816cdf0e10cSrcweir else 817cdf0e10cSrcweir { 818cdf0e10cSrcweir if(0x00 == aBitmapColor.GetIndex()) 819cdf0e10cSrcweir { 820cdf0e10cSrcweir nTransparency = 0x00; 821cdf0e10cSrcweir } 822cdf0e10cSrcweir } 823cdf0e10cSrcweir 824cdf0e10cSrcweir aTestBitmap.ReleaseAccess(pRead); 825cdf0e10cSrcweir } 826cdf0e10cSrcweir } 827cdf0e10cSrcweir break; 828cdf0e10cSrcweir } 829cdf0e10cSrcweir } 830cdf0e10cSrcweir } 831cdf0e10cSrcweir } 832cdf0e10cSrcweir 833cdf0e10cSrcweir return nTransparency; 834cdf0e10cSrcweir } 835cdf0e10cSrcweir 8365f27b83cSArmin Le Grand // ------------------------------------------------------------------ 8375f27b83cSArmin Le Grand 8385f27b83cSArmin Le Grand namespace 8395f27b83cSArmin Le Grand { 8405f27b83cSArmin Le Grand void impSmoothPoint(BitmapColor& rValue, const basegfx::B2DPoint& rSource, sal_Int32 nIntX, sal_Int32 nIntY, BitmapReadAccess& rRead) 8415f27b83cSArmin Le Grand { 8425f27b83cSArmin Le Grand double fDeltaX(rSource.getX() - nIntX); 8435f27b83cSArmin Le Grand double fDeltaY(rSource.getY() - nIntY); 8445f27b83cSArmin Le Grand sal_Int32 nIndX(0L); 8455f27b83cSArmin Le Grand sal_Int32 nIndY(0L); 8465f27b83cSArmin Le Grand 8475f27b83cSArmin Le Grand if(fDeltaX > 0.0 && nIntX + 1L < rRead.Width()) 8485f27b83cSArmin Le Grand { 8495f27b83cSArmin Le Grand nIndX++; 8505f27b83cSArmin Le Grand } 8515f27b83cSArmin Le Grand else if(fDeltaX < 0.0 && nIntX >= 1L) 8525f27b83cSArmin Le Grand { 8535f27b83cSArmin Le Grand fDeltaX = -fDeltaX; 8545f27b83cSArmin Le Grand nIndX--; 8555f27b83cSArmin Le Grand } 8565f27b83cSArmin Le Grand 8575f27b83cSArmin Le Grand if(fDeltaY > 0.0 && nIntY + 1L < rRead.Height()) 8585f27b83cSArmin Le Grand { 8595f27b83cSArmin Le Grand nIndY++; 8605f27b83cSArmin Le Grand } 8615f27b83cSArmin Le Grand else if(fDeltaY < 0.0 && nIntY >= 1L) 8625f27b83cSArmin Le Grand { 8635f27b83cSArmin Le Grand fDeltaY = -fDeltaY; 8645f27b83cSArmin Le Grand nIndY--; 8655f27b83cSArmin Le Grand } 8665f27b83cSArmin Le Grand 8675f27b83cSArmin Le Grand if(nIndX || nIndY) 8685f27b83cSArmin Le Grand { 8695f27b83cSArmin Le Grand const double fColorToReal(1.0 / 255.0); 8705f27b83cSArmin Le Grand double fR(rValue.GetRed() * fColorToReal); 8715f27b83cSArmin Le Grand double fG(rValue.GetGreen() * fColorToReal); 8725f27b83cSArmin Le Grand double fB(rValue.GetBlue() * fColorToReal); 8735f27b83cSArmin Le Grand double fRBottom(0.0), fGBottom(0.0), fBBottom(0.0); 8745f27b83cSArmin Le Grand 8755f27b83cSArmin Le Grand if(nIndX) 8765f27b83cSArmin Le Grand { 8775f27b83cSArmin Le Grand const double fMulA(fDeltaX * fColorToReal); 8785f27b83cSArmin Le Grand double fMulB(1.0 - fDeltaX); 8795f27b83cSArmin Le Grand const BitmapColor aTopPartner(rRead.GetColor(nIntY, nIntX + nIndX)); 8805f27b83cSArmin Le Grand 8815f27b83cSArmin Le Grand fR = (fR * fMulB) + (aTopPartner.GetRed() * fMulA); 8825f27b83cSArmin Le Grand fG = (fG * fMulB) + (aTopPartner.GetGreen() * fMulA); 8835f27b83cSArmin Le Grand fB = (fB * fMulB) + (aTopPartner.GetBlue() * fMulA); 8845f27b83cSArmin Le Grand 8855f27b83cSArmin Le Grand if(nIndY) 8865f27b83cSArmin Le Grand { 8875f27b83cSArmin Le Grand fMulB *= fColorToReal; 8885f27b83cSArmin Le Grand const BitmapColor aBottom(rRead.GetColor(nIntY + nIndY, nIntX)); 8895f27b83cSArmin Le Grand const BitmapColor aBottomPartner(rRead.GetColor(nIntY + nIndY, nIntX + nIndX)); 8905f27b83cSArmin Le Grand 8915f27b83cSArmin Le Grand fRBottom = (aBottom.GetRed() * fMulB) + (aBottomPartner.GetRed() * fMulA); 8925f27b83cSArmin Le Grand fGBottom = (aBottom.GetGreen() * fMulB) + (aBottomPartner.GetGreen() * fMulA); 8935f27b83cSArmin Le Grand fBBottom = (aBottom.GetBlue() * fMulB) + (aBottomPartner.GetBlue() * fMulA); 8945f27b83cSArmin Le Grand } 8955f27b83cSArmin Le Grand } 8965f27b83cSArmin Le Grand 8975f27b83cSArmin Le Grand if(nIndY) 8985f27b83cSArmin Le Grand { 8995f27b83cSArmin Le Grand if(!nIndX) 9005f27b83cSArmin Le Grand { 9015f27b83cSArmin Le Grand const BitmapColor aBottom(rRead.GetColor(nIntY + nIndY, nIntX)); 9025f27b83cSArmin Le Grand 9035f27b83cSArmin Le Grand fRBottom = aBottom.GetRed() * fColorToReal; 9045f27b83cSArmin Le Grand fGBottom = aBottom.GetGreen() * fColorToReal; 9055f27b83cSArmin Le Grand fBBottom = aBottom.GetBlue() * fColorToReal; 9065f27b83cSArmin Le Grand } 9075f27b83cSArmin Le Grand 9085f27b83cSArmin Le Grand const double fMulB(1.0 - fDeltaY); 9095f27b83cSArmin Le Grand 9105f27b83cSArmin Le Grand fR = (fR * fMulB) + (fRBottom * fDeltaY); 9115f27b83cSArmin Le Grand fG = (fG * fMulB) + (fGBottom * fDeltaY); 9125f27b83cSArmin Le Grand fB = (fB * fMulB) + (fBBottom * fDeltaY); 9135f27b83cSArmin Le Grand } 9145f27b83cSArmin Le Grand 9155f27b83cSArmin Le Grand rValue.SetRed((sal_uInt8)(fR * 255.0)); 9165f27b83cSArmin Le Grand rValue.SetGreen((sal_uInt8)(fG * 255.0)); 9175f27b83cSArmin Le Grand rValue.SetBlue((sal_uInt8)(fB * 255.0)); 9185f27b83cSArmin Le Grand } 9195f27b83cSArmin Le Grand } 9205f27b83cSArmin Le Grand 9215f27b83cSArmin Le Grand Bitmap impTransformBitmap( 9225f27b83cSArmin Le Grand const Bitmap& rSource, 9235f27b83cSArmin Le Grand const Size aDestinationSize, 9245f27b83cSArmin Le Grand const basegfx::B2DHomMatrix& rTransform, 9255f27b83cSArmin Le Grand bool bSmooth) 9265f27b83cSArmin Le Grand { 9275f27b83cSArmin Le Grand Bitmap aDestination(aDestinationSize, 24); 9285f27b83cSArmin Le Grand BitmapWriteAccess* pWrite = aDestination.AcquireWriteAccess(); 9295f27b83cSArmin Le Grand 9305f27b83cSArmin Le Grand if(pWrite) 9315f27b83cSArmin Le Grand { 9325f27b83cSArmin Le Grand const Size aContentSizePixel(rSource.GetSizePixel()); 9335f27b83cSArmin Le Grand BitmapReadAccess* pRead = (const_cast< Bitmap& >(rSource)).AcquireReadAccess(); 9345f27b83cSArmin Le Grand 9355f27b83cSArmin Le Grand if(pRead) 9365f27b83cSArmin Le Grand { 9375f27b83cSArmin Le Grand const Size aDestinationSizePixel(aDestination.GetSizePixel()); 9385f27b83cSArmin Le Grand bool bWorkWithIndex(rSource.GetBitCount() <= 8); 9395f27b83cSArmin Le Grand BitmapColor aOutside(BitmapColor(0xff, 0xff, 0xff)); 9405f27b83cSArmin Le Grand 9415f27b83cSArmin Le Grand for(sal_Int32 y(0L); y < aDestinationSizePixel.getHeight(); y++) 9425f27b83cSArmin Le Grand { 9435f27b83cSArmin Le Grand for(sal_Int32 x(0L); x < aDestinationSizePixel.getWidth(); x++) 9445f27b83cSArmin Le Grand { 9455f27b83cSArmin Le Grand const basegfx::B2DPoint aSourceCoor(rTransform * basegfx::B2DPoint(x, y)); 9465f27b83cSArmin Le Grand const sal_Int32 nIntX(basegfx::fround(aSourceCoor.getX())); 9475f27b83cSArmin Le Grand 9485f27b83cSArmin Le Grand if(nIntX >= 0L && nIntX < aContentSizePixel.getWidth()) 9495f27b83cSArmin Le Grand { 9505f27b83cSArmin Le Grand const sal_Int32 nIntY(basegfx::fround(aSourceCoor.getY())); 9515f27b83cSArmin Le Grand 9525f27b83cSArmin Le Grand if(nIntY >= 0L && nIntY < aContentSizePixel.getHeight()) 9535f27b83cSArmin Le Grand { 9545f27b83cSArmin Le Grand // inside pixel 9555f27b83cSArmin Le Grand BitmapColor aValue; 9565f27b83cSArmin Le Grand 9575f27b83cSArmin Le Grand if(bWorkWithIndex) 9585f27b83cSArmin Le Grand { 9595f27b83cSArmin Le Grand aValue = pRead->GetPaletteColor(pRead->GetPixelIndex(nIntY, nIntX)); 9605f27b83cSArmin Le Grand } 9615f27b83cSArmin Le Grand else 9625f27b83cSArmin Le Grand { 9635f27b83cSArmin Le Grand aValue = pRead->GetPixel(nIntY, nIntX); 9645f27b83cSArmin Le Grand } 9655f27b83cSArmin Le Grand 9665f27b83cSArmin Le Grand if(bSmooth) 9675f27b83cSArmin Le Grand { 9685f27b83cSArmin Le Grand impSmoothPoint(aValue, aSourceCoor, nIntX, nIntY, *pRead); 9695f27b83cSArmin Le Grand } 9705f27b83cSArmin Le Grand 9715f27b83cSArmin Le Grand pWrite->SetPixel(y, x, aValue); 9725f27b83cSArmin Le Grand continue; 9735f27b83cSArmin Le Grand } 9745f27b83cSArmin Le Grand } 9755f27b83cSArmin Le Grand 9765f27b83cSArmin Le Grand // here are outside pixels. Complete mask 9775f27b83cSArmin Le Grand if(bWorkWithIndex) 9785f27b83cSArmin Le Grand { 9795f27b83cSArmin Le Grand pWrite->SetPixel(y, x, aOutside); 9805f27b83cSArmin Le Grand } 9815f27b83cSArmin Le Grand } 9825f27b83cSArmin Le Grand } 9835f27b83cSArmin Le Grand 9845f27b83cSArmin Le Grand delete pRead; 9855f27b83cSArmin Le Grand } 9865f27b83cSArmin Le Grand 9875f27b83cSArmin Le Grand delete pWrite; 9885f27b83cSArmin Le Grand } 9895f27b83cSArmin Le Grand 9905f27b83cSArmin Le Grand rSource.AdaptBitCount(aDestination); 9915f27b83cSArmin Le Grand 9925f27b83cSArmin Le Grand return aDestination; 9935f27b83cSArmin Le Grand } 9945f27b83cSArmin Le Grand } // end of anonymous namespace 9955f27b83cSArmin Le Grand BitmapEx BitmapEx::TransformBitmapEx( 9965f27b83cSArmin Le Grand double fWidth, 9975f27b83cSArmin Le Grand double fHeight, 9985f27b83cSArmin Le Grand const basegfx::B2DHomMatrix& rTransformation) const 9995f27b83cSArmin Le Grand { 10005f27b83cSArmin Le Grand if(fWidth <= 1 || fHeight <= 1) 10015f27b83cSArmin Le Grand return BitmapEx(); 10025f27b83cSArmin Le Grand 10035f27b83cSArmin Le Grand // force destination to 24 bit, we want to smooth output 10045f27b83cSArmin Le Grand const Size aDestinationSize(basegfx::fround(fWidth), basegfx::fround(fHeight)); 10055f27b83cSArmin Le Grand static bool bDoSmoothAtAll(true); 10065f27b83cSArmin Le Grand const Bitmap aDestination(impTransformBitmap(GetBitmap(), aDestinationSize, rTransformation, bDoSmoothAtAll)); 10075f27b83cSArmin Le Grand 10085f27b83cSArmin Le Grand // create mask 10095f27b83cSArmin Le Grand if(IsTransparent()) 10105f27b83cSArmin Le Grand { 10115f27b83cSArmin Le Grand if(IsAlpha()) 10125f27b83cSArmin Le Grand { 10135f27b83cSArmin Le Grand const Bitmap aAlpha(impTransformBitmap(GetAlpha().GetBitmap(), aDestinationSize, rTransformation, bDoSmoothAtAll)); 10145f27b83cSArmin Le Grand return BitmapEx(aDestination, AlphaMask(aAlpha)); 10155f27b83cSArmin Le Grand } 10165f27b83cSArmin Le Grand else 10175f27b83cSArmin Le Grand { 10185f27b83cSArmin Le Grand const Bitmap aMask(impTransformBitmap(GetMask(), aDestinationSize, rTransformation, false)); 10195f27b83cSArmin Le Grand return BitmapEx(aDestination, aMask); 10205f27b83cSArmin Le Grand } 10215f27b83cSArmin Le Grand } 10225f27b83cSArmin Le Grand 10235f27b83cSArmin Le Grand return BitmapEx(aDestination); 10245f27b83cSArmin Le Grand } 10255f27b83cSArmin Le Grand 10265f27b83cSArmin Le Grand // ------------------------------------------------------------------ 10275f27b83cSArmin Le Grand 10285f27b83cSArmin Le Grand BitmapEx BitmapEx::getTransformed( 10295f27b83cSArmin Le Grand const basegfx::B2DHomMatrix& rTransformation, 10305f27b83cSArmin Le Grand double fMaximumArea) const 10315f27b83cSArmin Le Grand { 10325f27b83cSArmin Le Grand BitmapEx aRetval; 10335f27b83cSArmin Le Grand 10345f27b83cSArmin Le Grand if(IsEmpty()) 10355f27b83cSArmin Le Grand return aRetval; 10365f27b83cSArmin Le Grand 10375f27b83cSArmin Le Grand const sal_uInt32 nSourceWidth(GetSizePixel().Width()); 10385f27b83cSArmin Le Grand const sal_uInt32 nSourceHeight(GetSizePixel().Height()); 10395f27b83cSArmin Le Grand 10405f27b83cSArmin Le Grand if(!nSourceWidth || !nSourceHeight) 10415f27b83cSArmin Le Grand return aRetval; 10425f27b83cSArmin Le Grand 10435f27b83cSArmin Le Grand // Get dest range 10445f27b83cSArmin Le Grand basegfx::B2DRange aOutlineRange(0.0, 0.0, 1.0, 1.0); 10455f27b83cSArmin Le Grand aOutlineRange.transform(rTransformation); 10465f27b83cSArmin Le Grand 10475f27b83cSArmin Le Grand // get target size 10485f27b83cSArmin Le Grand double fWidth(aOutlineRange.getWidth()); 10495f27b83cSArmin Le Grand double fHeight(aOutlineRange.getHeight()); 10505f27b83cSArmin Le Grand 10515f27b83cSArmin Le Grand if(fWidth < 1.0 || fHeight < 1.0) 10525f27b83cSArmin Le Grand return aRetval; 10535f27b83cSArmin Le Grand 10545f27b83cSArmin Le Grand // test if discrete size (pixel) maybe too big and limit it 10555f27b83cSArmin Le Grand const double fArea(fWidth * fHeight); 10565f27b83cSArmin Le Grand const bool bNeedToReduce(fArea > fMaximumArea); 10575f27b83cSArmin Le Grand double fReduceFactor(1.0); 10585f27b83cSArmin Le Grand 10595f27b83cSArmin Le Grand if(bNeedToReduce) 10605f27b83cSArmin Le Grand { 10615f27b83cSArmin Le Grand fReduceFactor = sqrt(fMaximumArea / fArea); 10625f27b83cSArmin Le Grand fWidth *= fReduceFactor; 10635f27b83cSArmin Le Grand fHeight *= fReduceFactor; 10645f27b83cSArmin Le Grand } 10655f27b83cSArmin Le Grand 10665f27b83cSArmin Le Grand // Build complete transform from source pixels to target pixels. 10675f27b83cSArmin Le Grand // Start by scaling from source pixel size to unit coordinates 10685f27b83cSArmin Le Grand basegfx::B2DHomMatrix aTransform( 10695f27b83cSArmin Le Grand basegfx::tools::createScaleB2DHomMatrix( 10705f27b83cSArmin Le Grand 1.0 / nSourceWidth, 10715f27b83cSArmin Le Grand 1.0 / nSourceHeight)); 10725f27b83cSArmin Le Grand 10735f27b83cSArmin Le Grand // multiply with given transform which leads from unit coordinates inside 10745f27b83cSArmin Le Grand // aOutlineRange 10755f27b83cSArmin Le Grand aTransform = rTransformation * aTransform; 10765f27b83cSArmin Le Grand 10775f27b83cSArmin Le Grand // substract top-left of aOutlineRange 10785f27b83cSArmin Le Grand aTransform.translate(-aOutlineRange.getMinX(), -aOutlineRange.getMinY()); 10795f27b83cSArmin Le Grand 10805f27b83cSArmin Le Grand // scale to target pixels (if needed) 10815f27b83cSArmin Le Grand if(bNeedToReduce) 10825f27b83cSArmin Le Grand { 10835f27b83cSArmin Le Grand aTransform.scale(fReduceFactor, fReduceFactor); 10845f27b83cSArmin Le Grand } 10855f27b83cSArmin Le Grand 10865f27b83cSArmin Le Grand // invert to get transformation from target pixel coordiates to source pixels 10875f27b83cSArmin Le Grand aTransform.invert(); 10885f27b83cSArmin Le Grand 10895f27b83cSArmin Le Grand // create bitmap using source, destination and linear back-transformation 10905f27b83cSArmin Le Grand aRetval = TransformBitmapEx(fWidth, fHeight, aTransform); 10915f27b83cSArmin Le Grand 10925f27b83cSArmin Le Grand return aRetval; 10935f27b83cSArmin Le Grand } 10945f27b83cSArmin Le Grand 10955f27b83cSArmin Le Grand // ------------------------------------------------------------------ 10965f27b83cSArmin Le Grand 10975f27b83cSArmin Le Grand BitmapEx BitmapEx::ModifyBitmapEx(const basegfx::BColorModifierStack& rBColorModifierStack) const 10985f27b83cSArmin Le Grand { 10995f27b83cSArmin Le Grand Bitmap aChangedBitmap(GetBitmap()); 11005f27b83cSArmin Le Grand bool bDone(false); 11015f27b83cSArmin Le Grand 11025f27b83cSArmin Le Grand for(sal_uInt32 a(rBColorModifierStack.count()); a && !bDone; ) 11035f27b83cSArmin Le Grand { 11045f27b83cSArmin Le Grand const basegfx::BColorModifier& rModifier = rBColorModifierStack.getBColorModifier(--a); 11055f27b83cSArmin Le Grand 11065f27b83cSArmin Le Grand switch(rModifier.getMode()) 11075f27b83cSArmin Le Grand { 11085f27b83cSArmin Le Grand case basegfx::BCOLORMODIFYMODE_REPLACE : 11095f27b83cSArmin Le Grand { 11105f27b83cSArmin Le Grand // complete replace 11115f27b83cSArmin Le Grand if(IsTransparent()) 11125f27b83cSArmin Le Grand { 11135f27b83cSArmin Le Grand // clear bitmap with dest color 11145f27b83cSArmin Le Grand if(aChangedBitmap.GetBitCount() <= 8) 11155f27b83cSArmin Le Grand { 11165f27b83cSArmin Le Grand // do NOT use erase; for e.g. 8bit Bitmaps, the nearest color to the given 11175f27b83cSArmin Le Grand // erase color is determined and used -> this may be different from what is 11185f27b83cSArmin Le Grand // wanted here. Better create a new bitmap with the needed color explicitely 11195f27b83cSArmin Le Grand BitmapReadAccess* pReadAccess = aChangedBitmap.AcquireReadAccess(); 11205f27b83cSArmin Le Grand OSL_ENSURE(pReadAccess, "Got no Bitmap ReadAccess ?!?"); 11215f27b83cSArmin Le Grand 11225f27b83cSArmin Le Grand if(pReadAccess) 11235f27b83cSArmin Le Grand { 11245f27b83cSArmin Le Grand BitmapPalette aNewPalette(pReadAccess->GetPalette()); 11255f27b83cSArmin Le Grand aNewPalette[0] = BitmapColor(Color(rModifier.getBColor())); 11265f27b83cSArmin Le Grand aChangedBitmap = Bitmap( 11275f27b83cSArmin Le Grand aChangedBitmap.GetSizePixel(), 11285f27b83cSArmin Le Grand aChangedBitmap.GetBitCount(), 11295f27b83cSArmin Le Grand &aNewPalette); 11305f27b83cSArmin Le Grand delete pReadAccess; 11315f27b83cSArmin Le Grand } 11325f27b83cSArmin Le Grand } 11335f27b83cSArmin Le Grand else 11345f27b83cSArmin Le Grand { 11355f27b83cSArmin Le Grand aChangedBitmap.Erase(Color(rModifier.getBColor())); 11365f27b83cSArmin Le Grand } 11375f27b83cSArmin Le Grand } 11385f27b83cSArmin Le Grand else 11395f27b83cSArmin Le Grand { 11405f27b83cSArmin Le Grand // erase bitmap, caller will know to paint direct 11415f27b83cSArmin Le Grand aChangedBitmap.SetEmpty(); 11425f27b83cSArmin Le Grand } 11435f27b83cSArmin Le Grand 11445f27b83cSArmin Le Grand bDone = true; 11455f27b83cSArmin Le Grand break; 11465f27b83cSArmin Le Grand } 11475f27b83cSArmin Le Grand 11485f27b83cSArmin Le Grand default : // BCOLORMODIFYMODE_INTERPOLATE, BCOLORMODIFYMODE_GRAY, BCOLORMODIFYMODE_BLACKANDWHITE 11495f27b83cSArmin Le Grand { 11505f27b83cSArmin Le Grand BitmapWriteAccess* pContent = aChangedBitmap.AcquireWriteAccess(); 11515f27b83cSArmin Le Grand 11525f27b83cSArmin Le Grand if(pContent) 11535f27b83cSArmin Le Grand { 11545f27b83cSArmin Le Grand const double fConvertColor(1.0 / 255.0); 11555f27b83cSArmin Le Grand 11565f27b83cSArmin Le Grand for(sal_uInt32 y(0L); y < (sal_uInt32)pContent->Height(); y++) 11575f27b83cSArmin Le Grand { 11585f27b83cSArmin Le Grand for(sal_uInt32 x(0L); x < (sal_uInt32)pContent->Width(); x++) 11595f27b83cSArmin Le Grand { 11605f27b83cSArmin Le Grand const BitmapColor aBMCol(pContent->GetColor(y, x)); 11615f27b83cSArmin Le Grand const basegfx::BColor aBSource( 11625f27b83cSArmin Le Grand (double)aBMCol.GetRed() * fConvertColor, 11635f27b83cSArmin Le Grand (double)aBMCol.GetGreen() * fConvertColor, 11645f27b83cSArmin Le Grand (double)aBMCol.GetBlue() * fConvertColor); 11655f27b83cSArmin Le Grand const basegfx::BColor aBDest(rModifier.getModifiedColor(aBSource)); 11665f27b83cSArmin Le Grand 11675f27b83cSArmin Le Grand pContent->SetPixel(y, x, BitmapColor(Color(aBDest))); 11685f27b83cSArmin Le Grand } 11695f27b83cSArmin Le Grand } 11705f27b83cSArmin Le Grand 11715f27b83cSArmin Le Grand delete pContent; 11725f27b83cSArmin Le Grand } 11735f27b83cSArmin Le Grand 11745f27b83cSArmin Le Grand break; 11755f27b83cSArmin Le Grand } 11765f27b83cSArmin Le Grand } 11775f27b83cSArmin Le Grand } 11785f27b83cSArmin Le Grand 11795f27b83cSArmin Le Grand if(aChangedBitmap.IsEmpty()) 11805f27b83cSArmin Le Grand { 11815f27b83cSArmin Le Grand return BitmapEx(); 11825f27b83cSArmin Le Grand } 11835f27b83cSArmin Le Grand else 11845f27b83cSArmin Le Grand { 11855f27b83cSArmin Le Grand if(IsTransparent()) 11865f27b83cSArmin Le Grand { 11875f27b83cSArmin Le Grand if(IsAlpha()) 11885f27b83cSArmin Le Grand { 11895f27b83cSArmin Le Grand return BitmapEx(aChangedBitmap, GetAlpha()); 11905f27b83cSArmin Le Grand } 11915f27b83cSArmin Le Grand else 11925f27b83cSArmin Le Grand { 11935f27b83cSArmin Le Grand return BitmapEx(aChangedBitmap, GetMask()); 11945f27b83cSArmin Le Grand } 11955f27b83cSArmin Le Grand } 11965f27b83cSArmin Le Grand else 11975f27b83cSArmin Le Grand { 11985f27b83cSArmin Le Grand return BitmapEx(aChangedBitmap); 11995f27b83cSArmin Le Grand } 12005f27b83cSArmin Le Grand } 12015f27b83cSArmin Le Grand } 12025f27b83cSArmin Le Grand 1203*ff0f521cSArmin Le Grand // ----------------------------------------------------------------------------- 1204*ff0f521cSArmin Le Grand 1205*ff0f521cSArmin Le Grand BitmapEx VCL_DLLPUBLIC createBlendFrame( 1206*ff0f521cSArmin Le Grand const Size& rSize, 1207*ff0f521cSArmin Le Grand sal_uInt8 nAlpha, 1208*ff0f521cSArmin Le Grand Color aColorTopLeft, 1209*ff0f521cSArmin Le Grand Color aColorBottomRight) 1210*ff0f521cSArmin Le Grand { 1211*ff0f521cSArmin Le Grand const sal_uInt32 nW(rSize.Width()); 1212*ff0f521cSArmin Le Grand const sal_uInt32 nH(rSize.Height()); 1213*ff0f521cSArmin Le Grand 1214*ff0f521cSArmin Le Grand if(nW || nH) 1215*ff0f521cSArmin Le Grand { 1216*ff0f521cSArmin Le Grand Color aColTopRight(aColorTopLeft); 1217*ff0f521cSArmin Le Grand Color aColBottomLeft(aColorTopLeft); 1218*ff0f521cSArmin Le Grand const sal_uInt32 nDE(nW + nH); 1219*ff0f521cSArmin Le Grand 1220*ff0f521cSArmin Le Grand aColTopRight.Merge(aColorBottomRight, 255 - sal_uInt8((nW * 255) / nDE)); 1221*ff0f521cSArmin Le Grand aColBottomLeft.Merge(aColorBottomRight, 255 - sal_uInt8((nH * 255) / nDE)); 1222*ff0f521cSArmin Le Grand 1223*ff0f521cSArmin Le Grand return createBlendFrame(rSize, nAlpha, aColorTopLeft, aColTopRight, aColorBottomRight, aColBottomLeft); 1224*ff0f521cSArmin Le Grand } 1225*ff0f521cSArmin Le Grand 1226*ff0f521cSArmin Le Grand return BitmapEx(); 1227*ff0f521cSArmin Le Grand } 1228*ff0f521cSArmin Le Grand 1229*ff0f521cSArmin Le Grand BitmapEx VCL_DLLPUBLIC createBlendFrame( 1230*ff0f521cSArmin Le Grand const Size& rSize, 1231*ff0f521cSArmin Le Grand sal_uInt8 nAlpha, 1232*ff0f521cSArmin Le Grand Color aColorTopLeft, 1233*ff0f521cSArmin Le Grand Color aColorTopRight, 1234*ff0f521cSArmin Le Grand Color aColorBottomRight, 1235*ff0f521cSArmin Le Grand Color aColorBottomLeft) 1236*ff0f521cSArmin Le Grand { 1237*ff0f521cSArmin Le Grand static Size aLastSize(0, 0); 1238*ff0f521cSArmin Le Grand static sal_uInt8 nLastAlpha(0); 1239*ff0f521cSArmin Le Grand static Color aLastColorTopLeft(COL_BLACK); 1240*ff0f521cSArmin Le Grand static Color aLastColorTopRight(COL_BLACK); 1241*ff0f521cSArmin Le Grand static Color aLastColorBottomRight(COL_BLACK); 1242*ff0f521cSArmin Le Grand static Color aLastColorBottomLeft(COL_BLACK); 1243*ff0f521cSArmin Le Grand static BitmapEx aLastResult; 1244*ff0f521cSArmin Le Grand 1245*ff0f521cSArmin Le Grand if(aLastSize == rSize 1246*ff0f521cSArmin Le Grand && nLastAlpha == nAlpha 1247*ff0f521cSArmin Le Grand && aLastColorTopLeft == aLastColorTopLeft 1248*ff0f521cSArmin Le Grand && aLastColorTopRight == aLastColorTopRight 1249*ff0f521cSArmin Le Grand && aLastColorBottomRight == aLastColorBottomRight 1250*ff0f521cSArmin Le Grand && aLastColorBottomLeft == aLastColorBottomLeft) 1251*ff0f521cSArmin Le Grand { 1252*ff0f521cSArmin Le Grand return aLastResult; 1253*ff0f521cSArmin Le Grand } 1254*ff0f521cSArmin Le Grand 1255*ff0f521cSArmin Le Grand aLastSize = rSize; 1256*ff0f521cSArmin Le Grand nLastAlpha = nAlpha; 1257*ff0f521cSArmin Le Grand aLastColorTopLeft = aLastColorTopLeft; 1258*ff0f521cSArmin Le Grand aLastColorTopRight = aLastColorTopRight; 1259*ff0f521cSArmin Le Grand aLastColorBottomRight = aLastColorBottomRight; 1260*ff0f521cSArmin Le Grand aLastColorBottomLeft = aLastColorBottomLeft; 1261*ff0f521cSArmin Le Grand aLastResult.Clear(); 1262*ff0f521cSArmin Le Grand 1263*ff0f521cSArmin Le Grand const long nW(rSize.Width()); 1264*ff0f521cSArmin Le Grand const long nH(rSize.Height()); 1265*ff0f521cSArmin Le Grand 1266*ff0f521cSArmin Le Grand if(nW && nH) 1267*ff0f521cSArmin Le Grand { 1268*ff0f521cSArmin Le Grand sal_uInt8 aEraseTrans(0xff); 1269*ff0f521cSArmin Le Grand Bitmap aContent(rSize, 24); 1270*ff0f521cSArmin Le Grand AlphaMask aAlpha(rSize, &aEraseTrans); 1271*ff0f521cSArmin Le Grand 1272*ff0f521cSArmin Le Grand aContent.Erase(COL_BLACK); 1273*ff0f521cSArmin Le Grand 1274*ff0f521cSArmin Le Grand BitmapWriteAccess* pContent = aContent.AcquireWriteAccess(); 1275*ff0f521cSArmin Le Grand BitmapWriteAccess* pAlpha = aAlpha.AcquireWriteAccess(); 1276*ff0f521cSArmin Le Grand 1277*ff0f521cSArmin Le Grand if(pContent && pAlpha) 1278*ff0f521cSArmin Le Grand { 1279*ff0f521cSArmin Le Grand long x(0); 1280*ff0f521cSArmin Le Grand long y(0); 1281*ff0f521cSArmin Le Grand 1282*ff0f521cSArmin Le Grand // x == 0, y == 0 1283*ff0f521cSArmin Le Grand pContent->SetPixel(y, x, aColorTopLeft); 1284*ff0f521cSArmin Le Grand pAlpha->SetPixelIndex(y, x, nAlpha); 1285*ff0f521cSArmin Le Grand 1286*ff0f521cSArmin Le Grand for(x = 1; x < nW - 1; x++) // y == 0 1287*ff0f521cSArmin Le Grand { 1288*ff0f521cSArmin Le Grand Color aMix(aColorTopLeft); 1289*ff0f521cSArmin Le Grand 1290*ff0f521cSArmin Le Grand aMix.Merge(aColorTopRight, 255 - sal_uInt8((x * 255) / nW)); 1291*ff0f521cSArmin Le Grand pContent->SetPixel(y, x, aMix); 1292*ff0f521cSArmin Le Grand pAlpha->SetPixelIndex(y, x, nAlpha); 1293*ff0f521cSArmin Le Grand } 1294*ff0f521cSArmin Le Grand 1295*ff0f521cSArmin Le Grand // x == nW - 1, y == 0 1296*ff0f521cSArmin Le Grand pContent->SetPixel(y, x, aColorTopRight); 1297*ff0f521cSArmin Le Grand pAlpha->SetPixelIndex(y, x, nAlpha); 1298*ff0f521cSArmin Le Grand 1299*ff0f521cSArmin Le Grand for(y = 1; y < nH - 1; y++) // x == 0 and nW - 1 1300*ff0f521cSArmin Le Grand { 1301*ff0f521cSArmin Le Grand Color aMixA(aColorTopLeft); 1302*ff0f521cSArmin Le Grand Color aMixB(aColorTopRight); 1303*ff0f521cSArmin Le Grand 1304*ff0f521cSArmin Le Grand aMixA.Merge(aColorBottomLeft, 255 - sal_uInt8((y * 255) / nH)); 1305*ff0f521cSArmin Le Grand pContent->SetPixel(y, 0, aMixA); 1306*ff0f521cSArmin Le Grand pAlpha->SetPixelIndex(y, 0, nAlpha); 1307*ff0f521cSArmin Le Grand 1308*ff0f521cSArmin Le Grand aMixB.Merge(aColorBottomRight, 255 - sal_uInt8((y * 255) / nH)); 1309*ff0f521cSArmin Le Grand pContent->SetPixel(y, nW - 1, aMixB); 1310*ff0f521cSArmin Le Grand pAlpha->SetPixelIndex(y, nW - 1, nAlpha); 1311*ff0f521cSArmin Le Grand } 1312*ff0f521cSArmin Le Grand 1313*ff0f521cSArmin Le Grand x = 0; // x == 0, y == nH - 1 1314*ff0f521cSArmin Le Grand pContent->SetPixel(y, x, aColorBottomLeft); 1315*ff0f521cSArmin Le Grand pAlpha->SetPixelIndex(y, x, nAlpha); 1316*ff0f521cSArmin Le Grand 1317*ff0f521cSArmin Le Grand for(x = 1; x < nW - 1; x++) // y == nH - 1 1318*ff0f521cSArmin Le Grand { 1319*ff0f521cSArmin Le Grand Color aMix(aColorBottomLeft); 1320*ff0f521cSArmin Le Grand 1321*ff0f521cSArmin Le Grand aMix.Merge(aColorBottomRight, 255 - sal_uInt8(((x - 0)* 255) / nW)); 1322*ff0f521cSArmin Le Grand pContent->SetPixel(y, x, aMix); 1323*ff0f521cSArmin Le Grand pAlpha->SetPixelIndex(y, x, nAlpha); 1324*ff0f521cSArmin Le Grand } 1325*ff0f521cSArmin Le Grand 1326*ff0f521cSArmin Le Grand // x == nW - 1, y == nH - 1 1327*ff0f521cSArmin Le Grand pContent->SetPixel(y, x, aColorBottomRight); 1328*ff0f521cSArmin Le Grand pAlpha->SetPixelIndex(y, x, nAlpha); 1329*ff0f521cSArmin Le Grand 1330*ff0f521cSArmin Le Grand aContent.ReleaseAccess(pContent); 1331*ff0f521cSArmin Le Grand aAlpha.ReleaseAccess(pAlpha); 1332*ff0f521cSArmin Le Grand 1333*ff0f521cSArmin Le Grand aLastResult = BitmapEx(aContent, aAlpha); 1334*ff0f521cSArmin Le Grand } 1335*ff0f521cSArmin Le Grand else 1336*ff0f521cSArmin Le Grand { 1337*ff0f521cSArmin Le Grand if(pContent) 1338*ff0f521cSArmin Le Grand { 1339*ff0f521cSArmin Le Grand aContent.ReleaseAccess(pContent); 1340*ff0f521cSArmin Le Grand } 1341*ff0f521cSArmin Le Grand 1342*ff0f521cSArmin Le Grand if(pAlpha) 1343*ff0f521cSArmin Le Grand { 1344*ff0f521cSArmin Le Grand aAlpha.ReleaseAccess(pAlpha); 1345*ff0f521cSArmin Le Grand } 1346*ff0f521cSArmin Le Grand } 1347*ff0f521cSArmin Le Grand } 1348*ff0f521cSArmin Le Grand 1349*ff0f521cSArmin Le Grand return aLastResult; 1350*ff0f521cSArmin Le Grand } 1351*ff0f521cSArmin Le Grand 1352cdf0e10cSrcweir // ------------------------------------------------------------------ 135345fd3b9aSArmin Le Grand // eof 1354