diff options
-rw-r--r-- | include/vcl/bitmapfilter.hxx | 26 | ||||
-rw-r--r-- | include/vcl/bitmapscalesuper.hxx | 38 | ||||
-rw-r--r-- | vcl/Library_vcl.mk | 2 | ||||
-rw-r--r-- | vcl/source/bitmap/bitmapfilter.cxx | 19 | ||||
-rw-r--r-- | vcl/source/bitmap/bitmapscalesuper.cxx | 1013 | ||||
-rw-r--r-- | vcl/source/gdi/bitmap3.cxx | 813 |
6 files changed, 1102 insertions, 809 deletions
diff --git a/include/vcl/bitmapfilter.hxx b/include/vcl/bitmapfilter.hxx new file mode 100644 index 000000000000..37cdac1638d7 --- /dev/null +++ b/include/vcl/bitmapfilter.hxx @@ -0,0 +1,26 @@ +/* -*- Mode: C++; tab-width: 4; indent-tabs-mode: nil; c-basic-offset: 4 -*- */ +/* + * This file is part of the LibreOffice project. + * + * This Source Code Form is subject to the terms of the Mozilla Public + * License, v. 2.0. If a copy of the MPL was not distributed with this + * file, You can obtain one at http://mozilla.org/MPL/2.0/. + * + */ + +#ifndef INCLUDED_VCL_BITMAPFILTER_HXX +#define INCLUDED_VCL_BITMAPFILTER_HXX + +#include <vcl/bitmap.hxx> + +class VCL_DLLPUBLIC BitmapFilter +{ +public: + BitmapFilter(); + virtual ~BitmapFilter(); + virtual bool filter(Bitmap& rBitmap) = 0; +}; + +#endif // INCLUDED_VCL_BITMAPFILTER_HXX + +/* vim:set shiftwidth=4 softtabstop=4 expandtab: */ diff --git a/include/vcl/bitmapscalesuper.hxx b/include/vcl/bitmapscalesuper.hxx new file mode 100644 index 000000000000..3b59b9910ee1 --- /dev/null +++ b/include/vcl/bitmapscalesuper.hxx @@ -0,0 +1,38 @@ +/* -*- Mode: C++; tab-width: 4; indent-tabs-mode: nil; c-basic-offset: 4 -*- */ +/* + * This file is part of the LibreOffice project. + * + * This Source Code Form is subject to the terms of the Mozilla Public + * License, v. 2.0. If a copy of the MPL was not distributed with this + * file, You can obtain one at http://mozilla.org/MPL/2.0/. + * + * This file incorporates work covered by the following license notice: + * + * Licensed to the Apache Software Foundation (ASF) under one or more + * contributor license agreements. See the NOTICE file distributed + * with this work for additional information regarding copyright + * ownership. The ASF licenses this file to you under the Apache + * License, Version 2.0 (the "License"); you may not use this file + * except in compliance with the License. You may obtain a copy of + * the License at http://www.apache.org/licenses/LICENSE-2.0 . + */ + +#include <vcl/bitmapfilter.hxx> + +#ifndef INCLUDED_VCL_BITMAPSCALESUPER_HXX +#define INCLUDED_VCL_BITMAPSCALESUPER_HXX + +class VCL_DLLPUBLIC BitmapScaleSuper : public BitmapFilter +{ + double mrScaleX; + double mrScaleY; + +public: + BitmapScaleSuper(const double& rScaleX, const double& rScaleY); + virtual ~BitmapScaleSuper(); + virtual bool filter(Bitmap& rBitmap) SAL_OVERRIDE; +}; + +#endif // INCLUDED_VCL_BITMAPSCALESUPER_HXX + +/* vim:set shiftwidth=4 softtabstop=4 expandtab: */ diff --git a/vcl/Library_vcl.mk b/vcl/Library_vcl.mk index a1f2432caae7..72877b359b3a 100644 --- a/vcl/Library_vcl.mk +++ b/vcl/Library_vcl.mk @@ -271,6 +271,8 @@ $(eval $(call gb_Library_add_exception_objects,vcl,\ vcl/source/gdi/textlayout \ vcl/source/gdi/virdev \ vcl/source/gdi/wall \ + vcl/source/bitmap/bitmapfilter \ + vcl/source/bitmap/bitmapscalesuper \ vcl/source/helper/canvasbitmap \ vcl/source/helper/canvastools \ vcl/source/helper/evntpost \ diff --git a/vcl/source/bitmap/bitmapfilter.cxx b/vcl/source/bitmap/bitmapfilter.cxx new file mode 100644 index 000000000000..c04f3418c8e6 --- /dev/null +++ b/vcl/source/bitmap/bitmapfilter.cxx @@ -0,0 +1,19 @@ +/* -*- Mode: C++; tab-width: 4; indent-tabs-mode: nil; c-basic-offset: 4 -*- */ +/* + * This file is part of the LibreOffice project. + * + * This Source Code Form is subject to the terms of the Mozilla Public + * License, v. 2.0. If a copy of the MPL was not distributed with this + * file, You can obtain one at http://mozilla.org/MPL/2.0/. + * + */ + +#include <vcl/bitmapfilter.hxx> + +BitmapFilter::BitmapFilter() +{} + +BitmapFilter::~BitmapFilter() +{} + +/* vim:set shiftwidth=4 softtabstop=4 expandtab: */ diff --git a/vcl/source/bitmap/bitmapscalesuper.cxx b/vcl/source/bitmap/bitmapscalesuper.cxx new file mode 100644 index 000000000000..4d81c99c3acf --- /dev/null +++ b/vcl/source/bitmap/bitmapscalesuper.cxx @@ -0,0 +1,1013 @@ +/* -*- Mode: C++; tab-width: 4; indent-tabs-mode: nil; c-basic-offset: 4 -*- */ +/* + * This file is part of the LibreOffice project. + * + * This Source Code Form is subject to the terms of the Mozilla Public + * License, v. 2.0. If a copy of the MPL was not distributed with this + * file, You can obtain one at http://mozilla.org/MPL/2.0/. + * + * This file incorporates work covered by the following license notice: + * + * Licensed to the Apache Software Foundation (ASF) under one or more + * contributor license agreements. See the NOTICE file distributed + * with this work for additional information regarding copyright + * ownership. The ASF licenses this file to you under the Apache + * License, Version 2.0 (the "License"); you may not use this file + * except in compliance with the License. You may obtain a copy of + * the License at http://www.apache.org/licenses/LICENSE-2.0 . + */ + +#include <vcl/bmpacc.hxx> +#include <vcl/bitmapscalesuper.hxx> + +#include <boost/scoped_array.hpp> + +#define MAP( cVal0, cVal1, nFrac ) ((sal_uInt8)((((long)(cVal0)<<7L)+nFrac*((long)(cVal1)-(cVal0)))>>7L)) + +void generateMap(long nW, long nDstW, bool bHMirr, long* pMapIX, long* pMapFX) +{ + const double fRevScaleX = (nDstW > 1L) ? (double) (nW - 1) / (nDstW - 1) : 0.0; + + long nTemp = nW - 2L; + long nTempX = nW - 1L; + for (long nX = 0L; nX < nDstW; nX++) + { + double fTemp = nX * fRevScaleX; + if (bHMirr) + fTemp = nTempX - fTemp; + pMapIX[nX] = MinMax((long) fTemp, 0, nTemp); + pMapFX[nX] = (long) (fTemp - pMapIX[nX]) * 128.0; + } +} + +void scalePallete8bit(BitmapReadAccess* pAcc, BitmapWriteAccess* pWAcc, + long nStartX, long nEndX, long nStartY, long nEndY, + bool bVMirr, bool bHMirr) +{ + boost::scoped_array<long> pMapIX(new long[pWAcc->Width()]); + boost::scoped_array<long> pMapIY(new long[pWAcc->Height()]); + boost::scoped_array<long> pMapFX(new long[pWAcc->Width()]); + boost::scoped_array<long> pMapFY(new long[pWAcc->Height()]); + + generateMap(pAcc->Width(), pWAcc->Width(), bHMirr, pMapIX.get(), pMapFX.get()); + generateMap(pAcc->Height(), pWAcc->Height(), bVMirr, pMapIY.get(), pMapFY.get()); + + for( long nY = nStartY, nYDst = 0L; nY <= nEndY; nY++, nYDst++ ) + { + long nTempY = pMapIY[ nY ]; + long nTempFY = pMapFY[ nY ]; + Scanline pLine0 = pAcc->GetScanline( nTempY ); + Scanline pLine1 = pAcc->GetScanline( ++nTempY ); + + for(long nX = nStartX, nXDst = 0L; nX <= nEndX; nX++ ) + { + long nTempX = pMapIX[ nX ]; + long nTempFX = pMapFX[ nX ]; + + const BitmapColor& rCol0 = pAcc->GetPaletteColor( pLine0[ nTempX ] ); + const BitmapColor& rCol2 = pAcc->GetPaletteColor( pLine1[ nTempX ] ); + const BitmapColor& rCol1 = pAcc->GetPaletteColor( pLine0[ ++nTempX ] ); + const BitmapColor& rCol3 = pAcc->GetPaletteColor( pLine1[ nTempX ] ); + + sal_uInt8 cR0 = MAP( rCol0.GetRed(), rCol1.GetRed(), nTempFX ); + sal_uInt8 cG0 = MAP( rCol0.GetGreen(), rCol1.GetGreen(), nTempFX ); + sal_uInt8 cB0 = MAP( rCol0.GetBlue(), rCol1.GetBlue(), nTempFX ); + + sal_uInt8 cR1 = MAP( rCol2.GetRed(), rCol3.GetRed(), nTempFX ); + sal_uInt8 cG1 = MAP( rCol2.GetGreen(), rCol3.GetGreen(), nTempFX ); + sal_uInt8 cB1 = MAP( rCol2.GetBlue(), rCol3.GetBlue(), nTempFX ); + + BitmapColor aColRes( MAP( cR0, cR1, nTempFY ), + MAP( cG0, cG1, nTempFY ), + MAP( cB0, cB1, nTempFY ) ); + pWAcc->SetPixel( nYDst, nXDst++, aColRes ); + } + } +} + +void scalePalleteGeneral(BitmapReadAccess* pAcc, BitmapWriteAccess* pWAcc, + long nStartX, long nEndX, long nStartY, long nEndY, + bool bVMirr, bool bHMirr) + +{ + boost::scoped_array<long> pMapIX(new long[pWAcc->Width()]); + boost::scoped_array<long> pMapIY(new long[pWAcc->Height()]); + boost::scoped_array<long> pMapFX(new long[pWAcc->Width()]); + boost::scoped_array<long> pMapFY(new long[pWAcc->Height()]); + + generateMap(pAcc->Width(), pWAcc->Width(), bHMirr, pMapIX.get(), pMapFX.get()); + generateMap(pAcc->Height(), pWAcc->Height(), bVMirr, pMapIY.get(), pMapFY.get()); + + for( long nY = nStartY, nYDst = 0L; nY <= nEndY; nY++, nYDst++ ) + { + long nTempY = pMapIY[ nY ]; + long nTempFY = pMapFY[ nY ]; + + for( long nX = nStartX, nXDst = 0L; nX <= nEndX; nX++ ) + { + long nTempX = pMapIX[ nX ]; + long nTempFX = pMapFX[ nX ]; + + BitmapColor aCol0 = pAcc->GetPaletteColor( pAcc->GetPixelIndex( nTempY, nTempX ) ); + BitmapColor aCol1 = pAcc->GetPaletteColor( pAcc->GetPixelIndex( nTempY, ++nTempX ) ); + sal_uInt8 cR0 = MAP( aCol0.GetRed(), aCol1.GetRed(), nTempFX ); + sal_uInt8 cG0 = MAP( aCol0.GetGreen(), aCol1.GetGreen(), nTempFX ); + sal_uInt8 cB0 = MAP( aCol0.GetBlue(), aCol1.GetBlue(), nTempFX ); + + aCol1 = pAcc->GetPaletteColor( pAcc->GetPixelIndex( ++nTempY, nTempX ) ); + aCol0 = pAcc->GetPaletteColor( pAcc->GetPixelIndex( nTempY--, --nTempX ) ); + sal_uInt8 cR1 = MAP( aCol0.GetRed(), aCol1.GetRed(), nTempFX ); + sal_uInt8 cG1 = MAP( aCol0.GetGreen(), aCol1.GetGreen(), nTempFX ); + sal_uInt8 cB1 = MAP( aCol0.GetBlue(), aCol1.GetBlue(), nTempFX ); + + BitmapColor aColRes( MAP( cR0, cR1, nTempFY ), + MAP( cG0, cG1, nTempFY ), + MAP( cB0, cB1, nTempFY ) ); + pWAcc->SetPixel( nYDst, nXDst++, aColRes ); + } + } +} + +void scale24bitBGR(BitmapReadAccess* pAcc, BitmapWriteAccess* pWAcc, + long nStartX, long nEndX, long nStartY, long nEndY, + bool bVMirr, bool bHMirr) +{ + boost::scoped_array<long> pMapIX(new long[pWAcc->Width()]); + boost::scoped_array<long> pMapIY(new long[pWAcc->Height()]); + boost::scoped_array<long> pMapFX(new long[pWAcc->Width()]); + boost::scoped_array<long> pMapFY(new long[pWAcc->Height()]); + + generateMap(pAcc->Width(), pWAcc->Width(), bHMirr, pMapIX.get(), pMapFX.get()); + generateMap(pAcc->Height(), pWAcc->Height(), bVMirr, pMapIY.get(), pMapFY.get()); + + for( long nY = nStartY, nYDst = 0L; nY <= nEndY; nY++, nYDst++ ) + { + long nTempY = pMapIY[ nY ]; + long nTempFY = pMapFY[ nY ]; + Scanline pLine0 = pAcc->GetScanline( nTempY ); + Scanline pLine1 = pAcc->GetScanline( ++nTempY ); + + for( long nX = nStartX, nXDst = 0L; nX <= nEndX; nX++ ) + { + long nOff = 3L * pMapIX[ nX ]; + long nTempFX = pMapFX[ nX ]; + + Scanline pTmp0 = pLine0 + nOff ; + Scanline pTmp1 = pTmp0 + 3L; + sal_uInt8 cB0 = MAP( *pTmp0, *pTmp1, nTempFX ); + pTmp0++; pTmp1++; + sal_uInt8 cG0 = MAP( *pTmp0, *pTmp1, nTempFX ); + pTmp0++; pTmp1++; + sal_uInt8 cR0 = MAP( *pTmp0, *pTmp1, nTempFX ); + + pTmp1 = ( pTmp0 = pLine1 + nOff ) + 3L; + sal_uInt8 cB1 = MAP( *pTmp0, *pTmp1, nTempFX ); + pTmp0++; pTmp1++; + sal_uInt8 cG1 = MAP( *pTmp0, *pTmp1, nTempFX ); + pTmp0++; pTmp1++; + sal_uInt8 cR1 = MAP( *pTmp0, *pTmp1, nTempFX ); + + BitmapColor aColRes( MAP( cR0, cR1, nTempFY ), + MAP( cG0, cG1, nTempFY ), + MAP( cB0, cB1, nTempFY ) ); + pWAcc->SetPixel( nYDst, nXDst++, aColRes ); + } + } +} + +void scale24bitRGB(BitmapReadAccess* pAcc, BitmapWriteAccess* pWAcc, + long nStartX, long nEndX, long nStartY, long nEndY, + bool bVMirr, bool bHMirr) +{ + boost::scoped_array<long> pMapIX(new long[pWAcc->Width()]); + boost::scoped_array<long> pMapIY(new long[pWAcc->Height()]); + boost::scoped_array<long> pMapFX(new long[pWAcc->Width()]); + boost::scoped_array<long> pMapFY(new long[pWAcc->Height()]); + + generateMap(pAcc->Width(), pWAcc->Width(), bHMirr, pMapIX.get(), pMapFX.get()); + generateMap(pAcc->Height(), pWAcc->Height(), bVMirr, pMapIY.get(), pMapFY.get()); + + for( long nY = nStartY, nYDst = 0L; nY <= nEndY; nY++, nYDst++ ) + { + long nTempY = pMapIY[ nY ]; + long nTempFY = pMapFY[ nY ]; + Scanline pLine0 = pAcc->GetScanline( nTempY ); + Scanline pLine1 = pAcc->GetScanline( ++nTempY ); + + for( long nX = nStartX, nXDst = 0L; nX <= nEndX; nX++ ) + { + long nOff = 3L * pMapIX[ nX ]; + long nTempFX = pMapFX[ nX ]; + + Scanline pTmp0 = pLine0 + nOff; + Scanline pTmp1 = pTmp0 + 3L; + sal_uInt8 cR0 = MAP( *pTmp0, *pTmp1, nTempFX ); + pTmp0++; pTmp1++; + sal_uInt8 cG0 = MAP( *pTmp0, *pTmp1, nTempFX ); + pTmp0++; pTmp1++; + sal_uInt8 cB0 = MAP( *pTmp0, *pTmp1, nTempFX ); + + pTmp1 = ( pTmp0 = pLine1 + nOff ) + 3L; + sal_uInt8 cR1 = MAP( *pTmp0, *pTmp1, nTempFX ); + pTmp0++; pTmp1++; + sal_uInt8 cG1 = MAP( *pTmp0, *pTmp1, nTempFX ); + pTmp0++; pTmp1++; + sal_uInt8 cB1 = MAP( *pTmp0, *pTmp1, nTempFX ); + + BitmapColor aColRes( MAP( cR0, cR1, nTempFY ), + MAP( cG0, cG1, nTempFY ), + MAP( cB0, cB1, nTempFY ) ); + pWAcc->SetPixel( nYDst, nXDst++, aColRes ); + } + } +} + +void scaleNonPalleteGeneral(BitmapReadAccess* pAcc, BitmapWriteAccess* pWAcc, + long nStartX, long nEndX, long nStartY, long nEndY, + bool bVMirr, bool bHMirr) +{ + boost::scoped_array<long> pMapIX(new long[pWAcc->Width()]); + boost::scoped_array<long> pMapIY(new long[pWAcc->Height()]); + boost::scoped_array<long> pMapFX(new long[pWAcc->Width()]); + boost::scoped_array<long> pMapFY(new long[pWAcc->Height()]); + + generateMap(pAcc->Width(), pWAcc->Width(), bHMirr, pMapIX.get(), pMapFX.get()); + generateMap(pAcc->Height(), pWAcc->Height(), bVMirr, pMapIY.get(), pMapFY.get()); + + for( long nY = nStartY, nYDst = 0L; nY <= nEndY; nY++, nYDst++ ) + { + long nTempY = pMapIY[ nY ]; + long nTempFY = pMapFY[ nY ]; + + for( long nX = nStartX, nXDst = 0L; nX <= nEndX; nX++ ) + { + long nTempX = pMapIX[ nX ]; + long nTempFX = pMapFX[ nX ]; + + BitmapColor aCol0 = pAcc->GetPixel( nTempY, nTempX ); + BitmapColor aCol1 = pAcc->GetPixel( nTempY, ++nTempX ); + sal_uInt8 cR0 = MAP( aCol0.GetRed(), aCol1.GetRed(), nTempFX ); + sal_uInt8 cG0 = MAP( aCol0.GetGreen(), aCol1.GetGreen(), nTempFX ); + sal_uInt8 cB0 = MAP( aCol0.GetBlue(), aCol1.GetBlue(), nTempFX ); + + aCol1 = pAcc->GetPixel( ++nTempY, nTempX ); + aCol0 = pAcc->GetPixel( nTempY--, --nTempX ); + sal_uInt8 cR1 = MAP( aCol0.GetRed(), aCol1.GetRed(), nTempFX ); + sal_uInt8 cG1 = MAP( aCol0.GetGreen(), aCol1.GetGreen(), nTempFX ); + sal_uInt8 cB1 = MAP( aCol0.GetBlue(), aCol1.GetBlue(), nTempFX ); + + BitmapColor aColRes( MAP( cR0, cR1, nTempFY ), + MAP( cG0, cG1, nTempFY ), + MAP( cB0, cB1, nTempFY ) ); + pWAcc->SetPixel( nYDst, nXDst++, aColRes ); + } + } +} + +void scalePallete8bit2(BitmapReadAccess* pAcc, BitmapWriteAccess* pWAcc, + long nStartX, long nEndX, long nStartY, long nEndY, + bool bVMirr, bool bHMirr) +{ + boost::scoped_array<long> pMapIX(new long[pWAcc->Width()]); + boost::scoped_array<long> pMapIY(new long[pWAcc->Height()]); + boost::scoped_array<long> pMapFX(new long[pWAcc->Width()]); + boost::scoped_array<long> pMapFY(new long[pWAcc->Height()]); + + generateMap(pAcc->Width(), pWAcc->Width(), bHMirr, pMapIX.get(), pMapFX.get()); + generateMap(pAcc->Height(), pWAcc->Height(), bVMirr, pMapIY.get(), pMapFY.get()); + + const long nMax = 1 << 7L; + + for( long nY = nStartY , nYDst = 0L; nY <= nEndY; nY++, nYDst++ ) + { + long nTop = bVMirr ? ( nY + 1 ) : nY; + long nBottom = bVMirr ? nY : ( nY + 1 ) ; + + long nLineStart, nLineRange; + if( nY == nEndY ) + { + nLineStart = pMapIY[ nY ]; + nLineRange = 0; + } + else + { + nLineStart = pMapIY[ nTop ] ; + nLineRange = ( pMapIY[ nBottom ] == pMapIY[ nTop ] ) ? 1 :( pMapIY[ nBottom ] - pMapIY[ nTop ] ); + } + + for( long nX = nStartX , nXDst = 0L; nX <= nEndX; nX++ ) + { + long nLeft = bHMirr ? ( nX + 1 ) : nX; + long nRight = bHMirr ? nX : ( nX + 1 ) ; + + long nRowStart; + long nRowRange; + if( nX == nEndX ) + { + nRowStart = pMapIX[ nX ]; + nRowRange = 0; + } + else + { + nRowStart = pMapIX[ nLeft ]; + nRowRange = ( pMapIX[ nRight ] == pMapIX[ nLeft ] )? 1 : ( pMapIX[ nRight ] - pMapIX[ nLeft ] ); + } + + long nSumR = 0; + long nSumG = 0; + long nSumB = 0; + long nTotalWeightY = 0; + + for(int i = 0; i<= nLineRange; i++) + { + Scanline pTmpY = pAcc->GetScanline( nLineStart + i ); + long nSumRowR = 0; + long nSumRowG = 0; + long nSumRowB = 0; + long nTotalWeightX = 0; + + for(int j = 0; j <= nRowRange; j++) + { + const BitmapColor& rCol = pAcc->GetPaletteColor( pTmpY[ nRowStart + j ] ); + + if(nX == nEndX ) + { + nSumRowB += rCol.GetBlue() << 7L; + nSumRowG += rCol.GetGreen() << 7L; + nSumRowR += rCol.GetRed() << 7L; + nTotalWeightX += 1 << 7L; + } + else if( j == 0 ) + { + long nWeightX = (nMax- pMapFX[ nLeft ]) ; + nSumRowB += ( nWeightX *rCol.GetBlue()) ; + nSumRowG += ( nWeightX *rCol.GetGreen()) ; + nSumRowR += ( nWeightX *rCol.GetRed()) ; + nTotalWeightX += nWeightX; + } + else if ( nRowRange == j ) + { + long nWeightX = pMapFX[ nRight ] ; + nSumRowB += ( nWeightX *rCol.GetBlue() ); + nSumRowG += ( nWeightX *rCol.GetGreen() ); + nSumRowR += ( nWeightX *rCol.GetRed() ); + nTotalWeightX += nWeightX; + } + else + { + nSumRowB += rCol.GetBlue() << 7L; + nSumRowG += rCol.GetGreen() << 7L; + nSumRowR += rCol.GetRed() << 7L; + nTotalWeightX += 1 << 7L; + } + } + + long nWeightY = nMax; + if( nY == nEndY ) + nWeightY = nMax; + else if( i == 0 ) + nWeightY = nMax - pMapFY[ nTop ]; + else if( nLineRange == 1 ) + nWeightY = pMapFY[ nTop ]; + else if ( nLineRange == i ) + nWeightY = pMapFY[ nBottom ]; + + nSumB += nWeightY * ( nSumRowB / nTotalWeightX ); + nSumG += nWeightY * ( nSumRowG / nTotalWeightX ); + nSumR += nWeightY * ( nSumRowR / nTotalWeightX ); + nTotalWeightY += nWeightY; + } + + BitmapColor aColRes ( ( sal_uInt8 ) (( nSumR / nTotalWeightY ) ), + ( sal_uInt8 ) (( nSumG / nTotalWeightY) ), + ( sal_uInt8 ) (( nSumB / nTotalWeightY) ) ); + pWAcc->SetPixel( nYDst, nXDst++, aColRes ); + } + } +} + +void scalePalleteGeneral2(BitmapReadAccess* pAcc, BitmapWriteAccess* pWAcc, + long nStartX, long nEndX, long nStartY, long nEndY, + bool bVMirr, bool bHMirr) +{ + boost::scoped_array<long> pMapIX(new long[pWAcc->Width()]); + boost::scoped_array<long> pMapIY(new long[pWAcc->Height()]); + boost::scoped_array<long> pMapFX(new long[pWAcc->Width()]); + boost::scoped_array<long> pMapFY(new long[pWAcc->Height()]); + + generateMap(pAcc->Width(), pWAcc->Width(), bHMirr, pMapIX.get(), pMapFX.get()); + generateMap(pAcc->Height(), pWAcc->Height(), bVMirr, pMapIY.get(), pMapFY.get()); + + const long nMax = 1 << 7L; + + for( long nY = nStartY , nYDst = 0L; nY <= nEndY; nY++, nYDst++ ) + { + long nTop = bVMirr ? ( nY + 1 ) : nY; + long nBottom = bVMirr ? nY : ( nY + 1 ) ; + + long nLineStart, nLineRange; + if( nY ==nEndY ) + { + nLineStart = pMapIY[ nY ]; + nLineRange = 0; + } + else + { + nLineStart = pMapIY[ nTop ] ; + nLineRange = ( pMapIY[ nBottom ] == pMapIY[ nTop ] ) ? 1 :( pMapIY[ nBottom ] - pMapIY[ nTop ] ); + } + + for( long nX = nStartX , nXDst = 0L; nX <= nEndX; nX++ ) + { + long nLeft = bHMirr ? ( nX + 1 ) : nX; + long nRight = bHMirr ? nX : ( nX + 1 ) ; + + long nRowStart, nRowRange; + if( nX == nEndX ) + { + nRowStart = pMapIX[ nX ]; + nRowRange = 0; + } + else + { + nRowStart = pMapIX[ nLeft ]; + nRowRange = ( pMapIX[ nRight ] == pMapIX[ nLeft ] )? 1 : ( pMapIX[ nRight ] - pMapIX[ nLeft ] ); + } + + long nSumR = 0; + long nSumG = 0; + long nSumB = 0; + long nTotalWeightY = 0; + + for(int i = 0; i<= nLineRange; i++) + { + long nSumRowR = 0; + long nSumRowG = 0; + long nSumRowB = 0; + long nTotalWeightX = 0; + + for(int j = 0; j <= nRowRange; j++) + { + BitmapColor aCol0 = pAcc->GetPaletteColor ( pAcc->GetPixelIndex( nLineStart + i, nRowStart + j ) ); + + if(nX == nEndX ) + { + + nSumRowB += aCol0.GetBlue() << 7L; + nSumRowG += aCol0.GetGreen() << 7L; + nSumRowR += aCol0.GetRed() << 7L; + nTotalWeightX += 1 << 7L; + } + else if( j == 0 ) + { + + long nWeightX = (nMax- pMapFX[ nLeft ]) ; + nSumRowB += ( nWeightX *aCol0.GetBlue()) ; + nSumRowG += ( nWeightX *aCol0.GetGreen()) ; + nSumRowR += ( nWeightX *aCol0.GetRed()) ; + nTotalWeightX += nWeightX; + } + else if ( nRowRange == j ) + { + + long nWeightX = pMapFX[ nRight ] ; + nSumRowB += ( nWeightX *aCol0.GetBlue() ); + nSumRowG += ( nWeightX *aCol0.GetGreen() ); + nSumRowR += ( nWeightX *aCol0.GetRed() ); + nTotalWeightX += nWeightX; + } + else + { + + nSumRowB += aCol0.GetBlue() << 7L; + nSumRowG += aCol0.GetGreen() << 7L; + nSumRowR += aCol0.GetRed() << 7L; + nTotalWeightX += 1 << 7L; + } + } + + long nWeightY = nMax; + if( nY == nEndY ) + nWeightY = nMax; + else if( i == 0 ) + nWeightY = nMax - pMapFY[ nTop ]; + else if( nLineRange == 1 ) + nWeightY = pMapFY[ nTop ]; + else if ( nLineRange == i ) + nWeightY = pMapFY[ nBottom ]; + + nSumB += nWeightY * ( nSumRowB / nTotalWeightX ); + nSumG += nWeightY * ( nSumRowG / nTotalWeightX ); + nSumR += nWeightY * ( nSumRowR / nTotalWeightX ); + nTotalWeightY += nWeightY; + } + + BitmapColor aColRes( ( sal_uInt8 ) (( nSumR / nTotalWeightY ) ), + ( sal_uInt8 ) (( nSumG / nTotalWeightY) ), + ( sal_uInt8 ) (( nSumB / nTotalWeightY) )); + pWAcc->SetPixel( nYDst, nXDst++, aColRes ); + } + } +} + +void scale24bitBGR2(BitmapReadAccess* pAcc, BitmapWriteAccess* pWAcc, + long nStartX, long nEndX, long nStartY, long nEndY, + bool bVMirr, bool bHMirr) +{ + boost::scoped_array<long> pMapIX(new long[pWAcc->Width()]); + boost::scoped_array<long> pMapIY(new long[pWAcc->Height()]); + boost::scoped_array<long> pMapFX(new long[pWAcc->Width()]); + boost::scoped_array<long> pMapFY(new long[pWAcc->Height()]); + + generateMap(pAcc->Width(), pWAcc->Width(), bHMirr, pMapIX.get(), pMapFX.get()); + generateMap(pAcc->Height(), pWAcc->Height(), bVMirr, pMapIY.get(), pMapFY.get()); + + const long nMax = 1 << 7L; + + for( long nY = nStartY , nYDst = 0L; nY <= nEndY; nY++, nYDst++ ) + { + long nTop = bVMirr ? ( nY + 1 ) : nY; + long nBottom = bVMirr ? nY : ( nY + 1 ) ; + + long nLineStart; + long nLineRange; + if( nY ==nEndY ) + { + nLineStart = pMapIY[ nY ]; + nLineRange = 0; + } + else + { + nLineStart = pMapIY[ nTop ] ; + nLineRange = ( pMapIY[ nBottom ] == pMapIY[ nTop ] ) ? 1 :( pMapIY[ nBottom ] - pMapIY[ nTop ] ); + } + + for( long nX = nStartX , nXDst = 0L; nX <= nEndX; nX++ ) + { + long nLeft = bHMirr ? ( nX + 1 ) : nX; + long nRight = bHMirr ? nX : ( nX + 1 ) ; + + long nRowStart; + long nRowRange; + if( nX == nEndX ) + { + nRowStart = pMapIX[ nX ]; + nRowRange = 0; + } + else + { + nRowStart = pMapIX[ nLeft ]; + nRowRange = ( pMapIX[ nRight ] == pMapIX[ nLeft ] )? 1 : ( pMapIX[ nRight ] - pMapIX[ nLeft ] ); + } + + long nSumR = 0; + long nSumG = 0; + long nSumB = 0; + long nTotalWeightY = 0; + + for(int i = 0; i<= nLineRange; i++) + { + Scanline pTmpY = pAcc->GetScanline( nLineStart + i ); + Scanline pTmpX = pTmpY + 3L * nRowStart; + long nSumRowR = 0; + long nSumRowG = 0; + long nSumRowB = 0; + long nTotalWeightX = 0; + + for(int j = 0; j <= nRowRange; j++) + { + if(nX == nEndX ) + { + nSumRowB += ( *pTmpX ) << 7L;pTmpX++; + nSumRowG += ( *pTmpX ) << 7L;pTmpX++; + nSumRowR += ( *pTmpX ) << 7L;pTmpX++; + nTotalWeightX += 1 << 7L; + } + else if( j == 0 ) + { + long nWeightX = (nMax- pMapFX[ nLeft ]) ; + nSumRowB += ( nWeightX *( *pTmpX )) ;pTmpX++; + nSumRowG += ( nWeightX *( *pTmpX )) ;pTmpX++; + nSumRowR += ( nWeightX *( *pTmpX )) ;pTmpX++; + nTotalWeightX += nWeightX; + } + else if ( nRowRange == j ) + { + long nWeightX = pMapFX[ nRight ] ; + nSumRowB += ( nWeightX *( *pTmpX ) );pTmpX++; + nSumRowG += ( nWeightX *( *pTmpX ) );pTmpX++; + nSumRowR += ( nWeightX *( *pTmpX ) );pTmpX++; + nTotalWeightX += nWeightX; + } + else + { + nSumRowB += ( *pTmpX ) << 7L;pTmpX++; + nSumRowG += ( *pTmpX ) << 7L;pTmpX++; + nSumRowR += ( *pTmpX ) << 7L;pTmpX++; + nTotalWeightX += 1 << 7L; + } + } + + long nWeightY = nMax; + if( nY == nEndY ) + nWeightY = nMax; + else if( i == 0 ) + nWeightY = nMax - pMapFY[ nTop ]; + else if( nLineRange == 1 ) + nWeightY = pMapFY[ nTop ]; + else if ( nLineRange == i ) + nWeightY = pMapFY[ nBottom ]; + + nSumB += nWeightY * ( nSumRowB / nTotalWeightX ); + nSumG += nWeightY * ( nSumRowG / nTotalWeightX ); + nSumR += nWeightY * ( nSumRowR / nTotalWeightX ); + nTotalWeightY += nWeightY; + } + + BitmapColor aColRes( ( sal_uInt8 ) (( nSumR / nTotalWeightY ) ), + ( sal_uInt8 ) (( nSumG / nTotalWeightY) ), + ( sal_uInt8 ) (( nSumB / nTotalWeightY) )); + pWAcc->SetPixel( nYDst, nXDst++, aColRes ); + } + } +} + +void scale24bitRGB2(BitmapReadAccess* pAcc, BitmapWriteAccess* pWAcc, + long nStartX, long nEndX, long nStartY, long nEndY, + bool bVMirr, bool bHMirr) +{ + boost::scoped_array<long> pMapIX(new long[pWAcc->Width()]); + boost::scoped_array<long> pMapIY(new long[pWAcc->Height()]); + boost::scoped_array<long> pMapFX(new long[pWAcc->Width()]); + boost::scoped_array<long> pMapFY(new long[pWAcc->Height()]); + + generateMap(pAcc->Width(), pWAcc->Width(), bHMirr, pMapIX.get(), pMapFX.get()); + generateMap(pAcc->Height(), pWAcc->Height(), bVMirr, pMapIY.get(), pMapFY.get()); + + const long nMax = 1 << 7L; + + for( long nY = nStartY , nYDst = 0L; nY <= nEndY; nY++, nYDst++ ) + { + long nTop = bVMirr ? ( nY + 1 ) : nY; + long nBottom = bVMirr ? nY : ( nY + 1 ) ; + + long nLineStart, nLineRange; + if( nY ==nEndY ) + { + nLineStart = pMapIY[ nY ]; + nLineRange = 0; + } + else + { + nLineStart = pMapIY[ nTop ] ; + nLineRange = ( pMapIY[ nBottom ] == pMapIY[ nTop ] ) ? 1 :( pMapIY[ nBottom ] - pMapIY[ nTop ] ); + } + + for( long nX = nStartX , nXDst = 0L; nX <= nEndX; nX++ ) + { + long nLeft = bHMirr ? ( nX + 1 ) : nX; + long nRight = bHMirr ? nX : ( nX + 1 ) ; + + long nRowStart, nRowRange; + if( nX == nEndX ) + { + nRowStart = pMapIX[ nX ]; + nRowRange = 0; + } + else + { + nRowStart = pMapIX[ nLeft ]; + nRowRange = ( pMapIX[ nRight ] == pMapIX[ nLeft ] )? 1 : ( pMapIX[ nRight ] - pMapIX[ nLeft ] ); + } + + long nSumR = 0; + long nSumG = 0; + long nSumB = 0; + long nTotalWeightY = 0; + + for(int i = 0; i<= nLineRange; i++) + { + Scanline pTmpY = pAcc->GetScanline( nLineStart + i ); + Scanline pTmpX = pTmpY + 3L * nRowStart; + long nSumRowR = 0; + long nSumRowG = 0; + long nSumRowB = 0; + long nTotalWeightX = 0; + + for(int j = 0; j <= nRowRange; j++) + { + if(nX == nEndX ) + { + nSumRowR += ( *pTmpX ) << 7L;pTmpX++; + nSumRowG += ( *pTmpX ) << 7L;pTmpX++; + nSumRowB += ( *pTmpX ) << 7L;pTmpX++; + nTotalWeightX += 1 << 7L; + } + else if( j == 0 ) + { + long nWeightX = (nMax- pMapFX[ nLeft ]) ; + nSumRowR += ( nWeightX *( *pTmpX )) ;pTmpX++; + nSumRowG += ( nWeightX *( *pTmpX )) ;pTmpX++; + nSumRowB += ( nWeightX *( *pTmpX )) ;pTmpX++; + nTotalWeightX += nWeightX; + } + else if ( nRowRange == j ) + { + long nWeightX = pMapFX[ nRight ] ; + nSumRowR += ( nWeightX *( *pTmpX ) );pTmpX++; + nSumRowG += ( nWeightX *( *pTmpX ) );pTmpX++; + nSumRowB += ( nWeightX *( *pTmpX ) );pTmpX++; + nTotalWeightX += nWeightX; + } + else + { + nSumRowR += ( *pTmpX ) << 7L;pTmpX++; + nSumRowG += ( *pTmpX ) << 7L;pTmpX++; + nSumRowB += ( *pTmpX ) << 7L;pTmpX++; + nTotalWeightX += 1 << 7L; + } + } + + long nWeightY = nMax; + if( nY == nEndY ) + nWeightY = nMax; + else if( i == 0 ) + nWeightY = nMax - pMapFY[ nTop ]; + else if( nLineRange == 1 ) + nWeightY = pMapFY[ nTop ]; + else if ( nLineRange == i ) + nWeightY = pMapFY[ nBottom ]; + + nSumB += nWeightY * ( nSumRowB / nTotalWeightX ); + nSumG += nWeightY * ( nSumRowG / nTotalWeightX ); + nSumR += nWeightY * ( nSumRowR / nTotalWeightX ); + nTotalWeightY += nWeightY; + } + + BitmapColor aColRes( ( sal_uInt8 ) (( nSumR / nTotalWeightY ) ), + ( sal_uInt8 ) (( nSumG / nTotalWeightY) ), + ( sal_uInt8 ) (( nSumB / nTotalWeightY) )); + pWAcc->SetPixel( nYDst, nXDst++, aColRes ); + } + } +} + +void scaleNonPalleteGeneral2(BitmapReadAccess* pAcc, BitmapWriteAccess* pWAcc, + long nStartX, long nEndX, long nStartY, long nEndY, + bool bVMirr, bool bHMirr) +{ + boost::scoped_array<long> pMapIX(new long[pWAcc->Width()]); + boost::scoped_array<long> pMapIY(new long[pWAcc->Height()]); + boost::scoped_array<long> pMapFX(new long[pWAcc->Width()]); + boost::scoped_array<long> pMapFY(new long[pWAcc->Height()]); + + generateMap(pAcc->Width(), pWAcc->Width(), bHMirr, pMapIX.get(), pMapFX.get()); + generateMap(pAcc->Height(), pWAcc->Height(), bVMirr, pMapIY.get(), pMapFY.get()); + + const long nMax = 1 << 7L; + + for( long nY = nStartY , nYDst = 0L; nY <= nEndY; nY++, nYDst++ ) + { + long nTop = bVMirr ? ( nY + 1 ) : nY; + long nBottom = bVMirr ? nY : ( nY + 1 ) ; + + long nLineStart, nLineRange; + if( nY ==nEndY ) + { + nLineStart = pMapIY[ nY ]; + nLineRange = 0; + } + else + { + nLineStart = pMapIY[ nTop ] ; + nLineRange = ( pMapIY[ nBottom ] == pMapIY[ nTop ] ) ? 1 :( pMapIY[ nBottom ] - pMapIY[ nTop ] ); + } + + for( long nX = nStartX , nXDst = 0L; nX <= nEndX; nX++ ) + { + long nLeft = bHMirr ? ( nX + 1 ) : nX; + long nRight = bHMirr ? nX : ( nX + 1 ) ; + + long nRowStart, nRowRange; + if( nX == nEndX ) + { + nRowStart = pMapIX[ nX ]; + nRowRange = 0; + } + else + { + nRowStart = pMapIX[ nLeft ]; + nRowRange = ( pMapIX[ nRight ] == pMapIX[ nLeft ] )? 1 : ( pMapIX[ nRight ] - pMapIX[ nLeft ] ); + } + + long nSumR = 0; + long nSumG = 0; + long nSumB = 0; + long nTotalWeightY = 0; + + for(int i = 0; i<= nLineRange; i++) + { + long nSumRowR = 0; + long nSumRowG = 0; + long nSumRowB = 0; + long nTotalWeightX = 0; + + for(int j = 0; j <= nRowRange; j++) + { + BitmapColor aCol0 = pAcc->GetPixel( nLineStart + i, nRowStart + j ); + + if(nX == nEndX ) + { + + nSumRowB += aCol0.GetBlue() << 7L; + nSumRowG += aCol0.GetGreen() << 7L; + nSumRowR += aCol0.GetRed() << 7L; + nTotalWeightX += 1 << 7L; + } + else if( j == 0 ) + { + + long nWeightX = (nMax- pMapFX[ nLeft ]) ; + nSumRowB += ( nWeightX *aCol0.GetBlue()) ; + nSumRowG += ( nWeightX *aCol0.GetGreen()) ; + nSumRowR += ( nWeightX *aCol0.GetRed()) ; + nTotalWeightX += nWeightX; + } + else if ( nRowRange == j ) + { + + long nWeightX = pMapFX[ nRight ] ; + nSumRowB += ( nWeightX *aCol0.GetBlue() ); + nSumRowG += ( nWeightX *aCol0.GetGreen() ); + nSumRowR += ( nWeightX *aCol0.GetRed() ); + nTotalWeightX += nWeightX; + } + else + { + nSumRowB += aCol0.GetBlue() << 7L; + nSumRowG += aCol0.GetGreen() << 7L; + nSumRowR += aCol0.GetRed() << 7L; + nTotalWeightX += 1 << 7L; + } + } + + long nWeightY = nMax; + if( nY == nEndY ) + nWeightY = nMax; + else if( i == 0 ) + nWeightY = nMax - pMapFY[ nTop ]; + else if( nLineRange == 1 ) + nWeightY = pMapFY[ nTop ]; + else if ( nLineRange == i ) + nWeightY = pMapFY[ nBottom ]; + + nSumB += nWeightY * ( nSumRowB / nTotalWeightX ); + nSumG += nWeightY * ( nSumRowG / nTotalWeightX ); + nSumR += nWeightY * ( nSumRowR / nTotalWeightX ); + nTotalWeightY += nWeightY; + } + + BitmapColor aColRes( ( sal_uInt8 ) (( nSumR / nTotalWeightY) ), + ( sal_uInt8 ) (( nSumG / nTotalWeightY) ), + ( sal_uInt8 ) (( nSumB / nTotalWeightY) )); + pWAcc->SetPixel( nYDst, nXDst++, aColRes ); + + } + } +} + +BitmapScaleSuper::BitmapScaleSuper(const double& rScaleX, const double& rScaleY) : + mrScaleX(rScaleX), + mrScaleY(rScaleY) +{} + +BitmapScaleSuper::~BitmapScaleSuper() +{} + +bool BitmapScaleSuper::filter(Bitmap& rBitmap) +{ + bool bRet = false; + + const Size aSizePix(rBitmap.GetSizePixel()); + + bool bHMirr = mrScaleX < 0; + bool bVMirr = mrScaleY < 0; + + double fScaleX = std::fabs(mrScaleX); + double fScaleY = std::fabs(mrScaleY); + + const long nDstW = FRound(aSizePix.Width() * fScaleX); + const long nDstH = FRound(aSizePix.Height() * fScaleY); + + const double fScaleThresh = 0.6; + + if (nDstW <= 1L || nDstH <= 1L) + return false; + + Bitmap::ScopedReadAccess pReadAccess(rBitmap); + + Bitmap aOutBmp(Size(nDstW, nDstH), 24); + Bitmap::ScopedWriteAccess pWriteAccess(aOutBmp); + + const long nStartX = 0; + const long nStartY = 0; + const long nEndX = nDstW - 1L; + const long nEndY = nDstH - 1L; + + if (pReadAccess && pWriteAccess) + { + if( pReadAccess->HasPalette() ) + { + if( pReadAccess->GetScanlineFormat() == BMP_FORMAT_8BIT_PAL ) + { + if( fScaleX >= fScaleThresh && fScaleY >= fScaleThresh ) + { + scalePallete8bit(pReadAccess.get(), pWriteAccess.get(), + nStartX, nEndX, nStartY, nEndY, + bVMirr, bHMirr); + } + else + { + scalePallete8bit2(pReadAccess.get(), pWriteAccess.get(), + nStartX, nEndX, nStartY, nEndY, + bVMirr, bHMirr); + } + } + else + { + if( fScaleX >= fScaleThresh && fScaleY >= fScaleThresh ) + { + scalePalleteGeneral(pReadAccess.get(), pWriteAccess.get(), + nStartX, nEndX, nStartY, nEndY, + bVMirr, bHMirr); + } + else + { + scalePalleteGeneral2(pReadAccess.get(), pWriteAccess.get(), + nStartX, nEndX, nStartY, nEndY, + bVMirr, bHMirr); + } + } + } + else + { + if( pReadAccess->GetScanlineFormat() == BMP_FORMAT_24BIT_TC_BGR ) + { + if( fScaleX >= fScaleThresh && fScaleY >= fScaleThresh ) + { + scale24bitBGR(pReadAccess.get(), pWriteAccess.get(), + nStartX, nEndX, nStartY, nEndY, + bVMirr, bHMirr); + } + else + { + scale24bitBGR2(pReadAccess.get(), pWriteAccess.get(), + nStartX, nEndX, nStartY, nEndY, + bVMirr, bHMirr); + } + } + else if( pReadAccess->GetScanlineFormat() == BMP_FORMAT_24BIT_TC_RGB ) + { + if( fScaleX >= fScaleThresh && fScaleY >= fScaleThresh ) + { + scale24bitRGB(pReadAccess.get(), pWriteAccess.get(), + nStartX, nEndX, nStartY, nEndY, + bVMirr, bHMirr); + } + else + { + scale24bitRGB2(pReadAccess.get(), pWriteAccess.get(), + nStartX, nEndX, nStartY, nEndY, + bVMirr, bHMirr); + } + } + else + { + if( fScaleX >= fScaleThresh && fScaleY >= fScaleThresh ) + { + scaleNonPalleteGeneral(pReadAccess.get(), pWriteAccess.get(), + nStartX, nEndX, nStartY, nEndY, + bVMirr, bHMirr); + } + else + { + scaleNonPalleteGeneral2(pReadAccess.get(), pWriteAccess.get(), + nStartX, nEndX, nStartY, nEndY, + bVMirr, bHMirr); + } + } + } + + bRet = true; + } + + if( bRet ) + { + rBitmap.AdaptBitCount(aOutBmp); + rBitmap = aOutBmp; + } + + return bRet; +} + +/* vim:set shiftwidth=4 softtabstop=4 expandtab: */ diff --git a/vcl/source/gdi/bitmap3.cxx b/vcl/source/gdi/bitmap3.cxx index 7ee6405a4a6d..9600f9bcbb25 100644 --- a/vcl/source/gdi/bitmap3.cxx +++ b/vcl/source/gdi/bitmap3.cxx @@ -23,6 +23,7 @@ #include <vcl/bmpacc.hxx> #include <vcl/bitmapex.hxx> #include <vcl/bitmap.hxx> +#include <vcl/bitmapscalesuper.hxx> #include <boost/scoped_array.hpp> @@ -33,7 +34,6 @@ #define RGB15( _def_cR, _def_cG, _def_cB ) (((sal_uLong)(_def_cR)<<10UL)|((sal_uLong)(_def_cG)<<5UL)|(sal_uLong)(_def_cB)) #define GAMMA( _def_cVal, _def_InvGamma ) ((sal_uInt8)MinMax(FRound(pow( _def_cVal/255.0,_def_InvGamma)*255.0),0L,255L)) -#define MAP( cVal0, cVal1, nFrac ) ((sal_uInt8)((((long)(cVal0)<<7L)+nFrac*((long)(cVal1)-(cVal0)))>>7L)) #define CALC_ERRORS \ nTemp = p1T[nX++] >> 12; \ @@ -892,7 +892,7 @@ bool Bitmap::Scale( const double& rScaleX, const double& rScaleY, sal_uInt32 nSc bRetval = ImplScaleInterpolate( rScaleX, rScaleY ); break; } - case BMP_SCALE_SUPER : + case BMP_SCALE_SUPER: { if(GetSizePixel().Width() < 2 || GetSizePixel().Height() < 2) { @@ -901,8 +901,8 @@ bool Bitmap::Scale( const double& rScaleX, const double& rScaleY, sal_uInt32 nSc } else { - // #i121233# use method from symphony - bRetval = ImplScaleSuper( rScaleX, rScaleY ); + BitmapScaleSuper aScaleSuper(rScaleX, rScaleY); + bRetval = aScaleSuper.filter(*this); } break; } @@ -1268,811 +1268,6 @@ bool Bitmap::ImplScaleInterpolate( const double& rScaleX, const double& rScaleY return bRet; } -// #i121233# Added BMP_SCALE_SUPER from symphony code - -bool Bitmap::ImplScaleSuper( - const double& rScaleX, - const double& rScaleY ) -{ - const Size aSizePix( GetSizePixel() ); - bool bHMirr = ( rScaleX < 0 ); - bool bVMirr = ( rScaleY < 0 ); - double scaleX = bHMirr ? -rScaleX : rScaleX; - double scaleY = bVMirr ? -rScaleY : rScaleY; - const long nDstW = FRound( aSizePix.Width() * scaleX ); - const long nDstH = FRound( aSizePix.Height() * scaleY ); - const double fScaleThresh = 0.6; - bool bRet = false; - - if( ( nDstW > 1L ) && ( nDstH > 1L ) ) - { - Bitmap::ScopedReadAccess pAcc(*this); - Bitmap aOutBmp( Size( nDstW, nDstH ), 24 ); - Bitmap::ScopedWriteAccess pWAcc(aOutBmp); - boost::scoped_array<long> pMapIX(new long[ nDstW ]); - boost::scoped_array<long> pMapIY(new long[ nDstH ]); - boost::scoped_array<long> pMapFX(new long[ nDstW ]); - boost::scoped_array<long> pMapFY(new long[ nDstH ]); - const long nStartX = 0, nStartY = 0; - const long nEndX = nDstW - 1L; - const long nEndY = nDstH - 1L; - const long nMax = 1 << 7L; - - if( pAcc && pWAcc ) - { - const long nW = pAcc->Width() ; - const long nH = pAcc->Height() ; - const double fRevScaleX = ( nDstW > 1L ) ? ( (double) ( nW - 1 ) / ( nDstW - 1 ) ) : 0.0; - const double fRevScaleY = ( nDstH > 1L ) ? ( (double) ( nH - 1 ) / ( nDstH - 1 ) ) : 0.0; - - // create horizontal mapping table - for( long nX = 0L, nTempX = nW - 1L, nTemp = nW - 2L; nX < nDstW; nX++ ) - { - double fTemp = nX * fRevScaleX; - - if( bHMirr ) - fTemp = nTempX - fTemp; - pMapIX[ nX ] = MinMax( (long) fTemp, 0, nTemp ); - pMapFX[ nX ] = (long) ( ( fTemp - pMapIX[nX] ) * 128. ); - } - - // create vertical mapping table - for( long nY = 0L, nTempY = nH - 1L, nTemp = nH - 2L; nY < nDstH; nY++ ) - { - double fTemp = nY * fRevScaleY; - - if( bVMirr ) - fTemp = nTempY - fTemp; - pMapIY[ nY ] = MinMax( (long) fTemp, 0, nTemp ); - pMapFY[ nY ] = (long) ( ( fTemp - pMapIY[nY] ) * 128. ); - } - - if( pAcc->HasPalette() ) - { - if( pAcc->GetScanlineFormat() == BMP_FORMAT_8BIT_PAL ) - { - if( scaleX >= fScaleThresh && scaleY >= fScaleThresh ) - { - for( long nY = nStartY, nYDst = 0L; nY <= nEndY; nY++, nYDst++ ) - { - long nTempY = pMapIY[ nY ]; - long nTempFY = pMapFY[ nY ]; - Scanline pLine0 = pAcc->GetScanline( nTempY ); - Scanline pLine1 = pAcc->GetScanline( ++nTempY ); - - for(long nX = nStartX, nXDst = 0L; nX <= nEndX; nX++ ) - { - long nTempX = pMapIX[ nX ]; - long nTempFX = pMapFX[ nX ]; - - const BitmapColor& rCol0 = pAcc->GetPaletteColor( pLine0[ nTempX ] ); - const BitmapColor& rCol2 = pAcc->GetPaletteColor( pLine1[ nTempX ] ); - const BitmapColor& rCol1 = pAcc->GetPaletteColor( pLine0[ ++nTempX ] ); - const BitmapColor& rCol3 = pAcc->GetPaletteColor( pLine1[ nTempX ] ); - - sal_uInt8 cR0 = MAP( rCol0.GetRed(), rCol1.GetRed(), nTempFX ); - sal_uInt8 cG0 = MAP( rCol0.GetGreen(), rCol1.GetGreen(), nTempFX ); - sal_uInt8 cB0 = MAP( rCol0.GetBlue(), rCol1.GetBlue(), nTempFX ); - - sal_uInt8 cR1 = MAP( rCol2.GetRed(), rCol3.GetRed(), nTempFX ); - sal_uInt8 cG1 = MAP( rCol2.GetGreen(), rCol3.GetGreen(), nTempFX ); - sal_uInt8 cB1 = MAP( rCol2.GetBlue(), rCol3.GetBlue(), nTempFX ); - - BitmapColor aColRes( MAP( cR0, cR1, nTempFY ), - MAP( cG0, cG1, nTempFY ), - MAP( cB0, cB1, nTempFY ) ); - pWAcc->SetPixel( nYDst, nXDst++, aColRes ); - } - } - } - else - { - for( long nY = nStartY , nYDst = 0L; nY <= nEndY; nY++, nYDst++ ) - { - long nTop = bVMirr ? ( nY + 1 ) : nY; - long nBottom = bVMirr ? nY : ( nY + 1 ) ; - - long nLineStart, nLineRange; - if( nY == nEndY ) - { - nLineStart = pMapIY[ nY ]; - nLineRange = 0; - } - else - { - nLineStart = pMapIY[ nTop ] ; - nLineRange = ( pMapIY[ nBottom ] == pMapIY[ nTop ] ) ? 1 :( pMapIY[ nBottom ] - pMapIY[ nTop ] ); - } - - for( long nX = nStartX , nXDst = 0L; nX <= nEndX; nX++ ) - { - long nLeft = bHMirr ? ( nX + 1 ) : nX; - long nRight = bHMirr ? nX : ( nX + 1 ) ; - - long nRowStart; - long nRowRange; - if( nX == nEndX ) - { - nRowStart = pMapIX[ nX ]; - nRowRange = 0; - } - else - { - nRowStart = pMapIX[ nLeft ]; - nRowRange = ( pMapIX[ nRight ] == pMapIX[ nLeft ] )? 1 : ( pMapIX[ nRight ] - pMapIX[ nLeft ] ); - } - - long nSumR = 0; - long nSumG = 0; - long nSumB = 0; - long nTotalWeightY = 0; - - for(int i = 0; i<= nLineRange; i++) - { - Scanline pTmpY = pAcc->GetScanline( nLineStart + i ); - long nSumRowR = 0; - long nSumRowG = 0; - long nSumRowB = 0; - long nTotalWeightX = 0; - - for(int j = 0; j <= nRowRange; j++) - { - const BitmapColor& rCol = pAcc->GetPaletteColor( pTmpY[ nRowStart + j ] ); - - if(nX == nEndX ) - { - nSumRowB += rCol.GetBlue() << 7L; - nSumRowG += rCol.GetGreen() << 7L; - nSumRowR += rCol.GetRed() << 7L; - nTotalWeightX += 1 << 7L; - } - else if( j == 0 ) - { - long nWeightX = (nMax- pMapFX[ nLeft ]) ; - nSumRowB += ( nWeightX *rCol.GetBlue()) ; - nSumRowG += ( nWeightX *rCol.GetGreen()) ; - nSumRowR += ( nWeightX *rCol.GetRed()) ; - nTotalWeightX += nWeightX; - } - else if ( nRowRange == j ) - { - long nWeightX = pMapFX[ nRight ] ; - nSumRowB += ( nWeightX *rCol.GetBlue() ); - nSumRowG += ( nWeightX *rCol.GetGreen() ); - nSumRowR += ( nWeightX *rCol.GetRed() ); - nTotalWeightX += nWeightX; - } - else - { - nSumRowB += rCol.GetBlue() << 7L; - nSumRowG += rCol.GetGreen() << 7L; - nSumRowR += rCol.GetRed() << 7L; - nTotalWeightX += 1 << 7L; - } - } - - long nWeightY = nMax; - if( nY == nEndY ) - nWeightY = nMax; - else if( i == 0 ) - nWeightY = nMax - pMapFY[ nTop ]; - else if( nLineRange == 1 ) - nWeightY = pMapFY[ nTop ]; - else if ( nLineRange == i ) - nWeightY = pMapFY[ nBottom ]; - - nSumB += nWeightY * ( nSumRowB / nTotalWeightX ); - nSumG += nWeightY * ( nSumRowG / nTotalWeightX ); - nSumR += nWeightY * ( nSumRowR / nTotalWeightX ); - nTotalWeightY += nWeightY; - } - - BitmapColor aColRes ( ( sal_uInt8 ) (( nSumR / nTotalWeightY ) ), - ( sal_uInt8 ) (( nSumG / nTotalWeightY) ), - ( sal_uInt8 ) (( nSumB / nTotalWeightY) ) ); - pWAcc->SetPixel( nYDst, nXDst++, aColRes ); - } - } - } - } - else - { - if( scaleX >= fScaleThresh && scaleY >= fScaleThresh ) - { - for( long nY = nStartY, nYDst = 0L; nY <= nEndY; nY++, nYDst++ ) - { - long nTempY = pMapIY[ nY ]; - long nTempFY = pMapFY[ nY ]; - - for( long nX = nStartX, nXDst = 0L; nX <= nEndX; nX++ ) - { - long nTempX = pMapIX[ nX ]; - long nTempFX = pMapFX[ nX ]; - - BitmapColor aCol0 = pAcc->GetPaletteColor( pAcc->GetPixelIndex( nTempY, nTempX ) ); - BitmapColor aCol1 = pAcc->GetPaletteColor( pAcc->GetPixelIndex( nTempY, ++nTempX ) ); - sal_uInt8 cR0 = MAP( aCol0.GetRed(), aCol1.GetRed(), nTempFX ); - sal_uInt8 cG0 = MAP( aCol0.GetGreen(), aCol1.GetGreen(), nTempFX ); - sal_uInt8 cB0 = MAP( aCol0.GetBlue(), aCol1.GetBlue(), nTempFX ); - - aCol1 = pAcc->GetPaletteColor( pAcc->GetPixelIndex( ++nTempY, nTempX ) ); - aCol0 = pAcc->GetPaletteColor( pAcc->GetPixelIndex( nTempY--, --nTempX ) ); - sal_uInt8 cR1 = MAP( aCol0.GetRed(), aCol1.GetRed(), nTempFX ); - sal_uInt8 cG1 = MAP( aCol0.GetGreen(), aCol1.GetGreen(), nTempFX ); - sal_uInt8 cB1 = MAP( aCol0.GetBlue(), aCol1.GetBlue(), nTempFX ); - - BitmapColor aColRes( MAP( cR0, cR1, nTempFY ), - MAP( cG0, cG1, nTempFY ), - MAP( cB0, cB1, nTempFY ) ); - pWAcc->SetPixel( nYDst, nXDst++, aColRes ); - } - } - - } - else - { - for( long nY = nStartY , nYDst = 0L; nY <= nEndY; nY++, nYDst++ ) - { - long nTop = bVMirr ? ( nY + 1 ) : nY; - long nBottom = bVMirr ? nY : ( nY + 1 ) ; - - long nLineStart, nLineRange; - if( nY ==nEndY ) - { - nLineStart = pMapIY[ nY ]; - nLineRange = 0; - } - else - { - nLineStart = pMapIY[ nTop ] ; - nLineRange = ( pMapIY[ nBottom ] == pMapIY[ nTop ] ) ? 1 :( pMapIY[ nBottom ] - pMapIY[ nTop ] ); - } - - for( long nX = nStartX , nXDst = 0L; nX <= nEndX; nX++ ) - { - long nLeft = bHMirr ? ( nX + 1 ) : nX; - long nRight = bHMirr ? nX : ( nX + 1 ) ; - - long nRowStart, nRowRange; - if( nX == nEndX ) - { - nRowStart = pMapIX[ nX ]; - nRowRange = 0; - } - else - { - nRowStart = pMapIX[ nLeft ]; - nRowRange = ( pMapIX[ nRight ] == pMapIX[ nLeft ] )? 1 : ( pMapIX[ nRight ] - pMapIX[ nLeft ] ); - } - - long nSumR = 0; - long nSumG = 0; - long nSumB = 0; - long nTotalWeightY = 0; - - for(int i = 0; i<= nLineRange; i++) - { - long nSumRowR = 0; - long nSumRowG = 0; - long nSumRowB = 0; - long nTotalWeightX = 0; - - for(int j = 0; j <= nRowRange; j++) - { - BitmapColor aCol0 = pAcc->GetPaletteColor ( pAcc->GetPixelIndex( nLineStart + i, nRowStart + j ) ); - - if(nX == nEndX ) - { - - nSumRowB += aCol0.GetBlue() << 7L; - nSumRowG += aCol0.GetGreen() << 7L; - nSumRowR += aCol0.GetRed() << 7L; - nTotalWeightX += 1 << 7L; - } - else if( j == 0 ) - { - - long nWeightX = (nMax- pMapFX[ nLeft ]) ; - nSumRowB += ( nWeightX *aCol0.GetBlue()) ; - nSumRowG += ( nWeightX *aCol0.GetGreen()) ; - nSumRowR += ( nWeightX *aCol0.GetRed()) ; - nTotalWeightX += nWeightX; - } - else if ( nRowRange == j ) - { - - long nWeightX = pMapFX[ nRight ] ; - nSumRowB += ( nWeightX *aCol0.GetBlue() ); - nSumRowG += ( nWeightX *aCol0.GetGreen() ); - nSumRowR += ( nWeightX *aCol0.GetRed() ); - nTotalWeightX += nWeightX; - } - else - { - - nSumRowB += aCol0.GetBlue() << 7L; - nSumRowG += aCol0.GetGreen() << 7L; - nSumRowR += aCol0.GetRed() << 7L; - nTotalWeightX += 1 << 7L; - } - } - - long nWeightY = nMax; - if( nY == nEndY ) - nWeightY = nMax; - else if( i == 0 ) - nWeightY = nMax - pMapFY[ nTop ]; - else if( nLineRange == 1 ) - nWeightY = pMapFY[ nTop ]; - else if ( nLineRange == i ) - nWeightY = pMapFY[ nBottom ]; - - nSumB += nWeightY * ( nSumRowB / nTotalWeightX ); - nSumG += nWeightY * ( nSumRowG / nTotalWeightX ); - nSumR += nWeightY * ( nSumRowR / nTotalWeightX ); - nTotalWeightY += nWeightY; - } - - BitmapColor aColRes( ( sal_uInt8 ) (( nSumR / nTotalWeightY ) ), - ( sal_uInt8 ) (( nSumG / nTotalWeightY) ), - ( sal_uInt8 ) (( nSumB / nTotalWeightY) )); - pWAcc->SetPixel( nYDst, nXDst++, aColRes ); - } - } - } - } - } - else - { - if( pAcc->GetScanlineFormat() == BMP_FORMAT_24BIT_TC_BGR ) - { - if( scaleX >= fScaleThresh && scaleY >= fScaleThresh ) - { - for( long nY = nStartY, nYDst = 0L; nY <= nEndY; nY++, nYDst++ ) - { - long nTempY = pMapIY[ nY ]; - long nTempFY = pMapFY[ nY ]; - Scanline pLine0 = pAcc->GetScanline( nTempY ); - Scanline pLine1 = pAcc->GetScanline( ++nTempY ); - - for( long nX = nStartX, nXDst = 0L; nX <= nEndX; nX++ ) - { - long nOff = 3L * pMapIX[ nX ]; - long nTempFX = pMapFX[ nX ]; - - Scanline pTmp0 = pLine0 + nOff ; - Scanline pTmp1 = pTmp0 + 3L; - sal_uInt8 cB0 = MAP( *pTmp0, *pTmp1, nTempFX ); pTmp0++; pTmp1++; - sal_uInt8 cG0 = MAP( *pTmp0, *pTmp1, nTempFX ); pTmp0++; pTmp1++; - sal_uInt8 cR0 = MAP( *pTmp0, *pTmp1, nTempFX ); - - pTmp1 = ( pTmp0 = pLine1 + nOff ) + 3L; - sal_uInt8 cB1 = MAP( *pTmp0, *pTmp1, nTempFX ); pTmp0++; pTmp1++; - sal_uInt8 cG1 = MAP( *pTmp0, *pTmp1, nTempFX ); pTmp0++; pTmp1++; - sal_uInt8 cR1 = MAP( *pTmp0, *pTmp1, nTempFX ); - - BitmapColor aColRes( MAP( cR0, cR1, nTempFY ), - MAP( cG0, cG1, nTempFY ), - MAP( cB0, cB1, nTempFY ) ); - pWAcc->SetPixel( nYDst, nXDst++, aColRes ); - } - } - } - else - { - for( long nY = nStartY , nYDst = 0L; nY <= nEndY; nY++, nYDst++ ) - { - long nTop = bVMirr ? ( nY + 1 ) : nY; - long nBottom = bVMirr ? nY : ( nY + 1 ) ; - - long nLineStart; - long nLineRange; - if( nY ==nEndY ) - { - nLineStart = pMapIY[ nY ]; - nLineRange = 0; - } - else - { - nLineStart = pMapIY[ nTop ] ; - nLineRange = ( pMapIY[ nBottom ] == pMapIY[ nTop ] ) ? 1 :( pMapIY[ nBottom ] - pMapIY[ nTop ] ); - } - - for( long nX = nStartX , nXDst = 0L; nX <= nEndX; nX++ ) - { - long nLeft = bHMirr ? ( nX + 1 ) : nX; - long nRight = bHMirr ? nX : ( nX + 1 ) ; - - long nRowStart; - long nRowRange; - if( nX == nEndX ) - { - nRowStart = pMapIX[ nX ]; - nRowRange = 0; - } - else - { - nRowStart = pMapIX[ nLeft ]; - nRowRange = ( pMapIX[ nRight ] == pMapIX[ nLeft ] )? 1 : ( pMapIX[ nRight ] - pMapIX[ nLeft ] ); - } - - long nSumR = 0; - long nSumG = 0; - long nSumB = 0; - long nTotalWeightY = 0; - - for(int i = 0; i<= nLineRange; i++) - { - Scanline pTmpY = pAcc->GetScanline( nLineStart + i ); - Scanline pTmpX = pTmpY + 3L * nRowStart; - long nSumRowR = 0; - long nSumRowG = 0; - long nSumRowB = 0; - long nTotalWeightX = 0; - - for(int j = 0; j <= nRowRange; j++) - { - if(nX == nEndX ) - { - nSumRowB += ( *pTmpX ) << 7L;pTmpX++; - nSumRowG += ( *pTmpX ) << 7L;pTmpX++; - nSumRowR += ( *pTmpX ) << 7L;pTmpX++; - nTotalWeightX += 1 << 7L; - } - else if( j == 0 ) - { - long nWeightX = (nMax- pMapFX[ nLeft ]) ; - nSumRowB += ( nWeightX *( *pTmpX )) ;pTmpX++; - nSumRowG += ( nWeightX *( *pTmpX )) ;pTmpX++; - nSumRowR += ( nWeightX *( *pTmpX )) ;pTmpX++; - nTotalWeightX += nWeightX; - } - else if ( nRowRange == j ) - { - long nWeightX = pMapFX[ nRight ] ; - nSumRowB += ( nWeightX *( *pTmpX ) );pTmpX++; - nSumRowG += ( nWeightX *( *pTmpX ) );pTmpX++; - nSumRowR += ( nWeightX *( *pTmpX ) );pTmpX++; - nTotalWeightX += nWeightX; - } - else - { - nSumRowB += ( *pTmpX ) << 7L;pTmpX++; - nSumRowG += ( *pTmpX ) << 7L;pTmpX++; - nSumRowR += ( *pTmpX ) << 7L;pTmpX++; - nTotalWeightX += 1 << 7L; - } - } - - long nWeightY = nMax; - if( nY == nEndY ) - nWeightY = nMax; - else if( i == 0 ) - nWeightY = nMax - pMapFY[ nTop ]; - else if( nLineRange == 1 ) - nWeightY = pMapFY[ nTop ]; - else if ( nLineRange == i ) - nWeightY = pMapFY[ nBottom ]; - - nSumB += nWeightY * ( nSumRowB / nTotalWeightX ); - nSumG += nWeightY * ( nSumRowG / nTotalWeightX ); - nSumR += nWeightY * ( nSumRowR / nTotalWeightX ); - nTotalWeightY += nWeightY; - } - - BitmapColor aColRes( ( sal_uInt8 ) (( nSumR / nTotalWeightY ) ), - ( sal_uInt8 ) (( nSumG / nTotalWeightY) ), - ( sal_uInt8 ) (( nSumB / nTotalWeightY) )); - pWAcc->SetPixel( nYDst, nXDst++, aColRes ); - } - } - } - } - else if( pAcc->GetScanlineFormat() == BMP_FORMAT_24BIT_TC_RGB ) - { - if( scaleX >= fScaleThresh && scaleY >= fScaleThresh ) - { - for( long nY = nStartY, nYDst = 0L; nY <= nEndY; nY++, nYDst++ ) - { - long nTempY = pMapIY[ nY ]; - long nTempFY = pMapFY[ nY ]; - Scanline pLine0 = pAcc->GetScanline( nTempY ); - Scanline pLine1 = pAcc->GetScanline( ++nTempY ); - - for( long nX = nStartX, nXDst = 0L; nX <= nEndX; nX++ ) - { - long nOff = 3L * pMapIX[ nX ]; - long nTempFX = pMapFX[ nX ]; - - Scanline pTmp0 = pLine0 + nOff; - Scanline pTmp1 = pTmp0 + 3L; - sal_uInt8 cR0 = MAP( *pTmp0, *pTmp1, nTempFX ); pTmp0++; pTmp1++; - sal_uInt8 cG0 = MAP( *pTmp0, *pTmp1, nTempFX ); pTmp0++; pTmp1++; - sal_uInt8 cB0 = MAP( *pTmp0, *pTmp1, nTempFX ); - - pTmp1 = ( pTmp0 = pLine1 + nOff ) + 3L; - sal_uInt8 cR1 = MAP( *pTmp0, *pTmp1, nTempFX ); pTmp0++; pTmp1++; - sal_uInt8 cG1 = MAP( *pTmp0, *pTmp1, nTempFX ); pTmp0++; pTmp1++; - sal_uInt8 cB1 = MAP( *pTmp0, *pTmp1, nTempFX ); - - BitmapColor aColRes( MAP( cR0, cR1, nTempFY ), - MAP( cG0, cG1, nTempFY ), - MAP( cB0, cB1, nTempFY ) ); - pWAcc->SetPixel( nYDst, nXDst++, aColRes ); - } - } - } - else - { - for( long nY = nStartY , nYDst = 0L; nY <= nEndY; nY++, nYDst++ ) - { - long nTop = bVMirr ? ( nY + 1 ) : nY; - long nBottom = bVMirr ? nY : ( nY + 1 ) ; - - long nLineStart, nLineRange; - if( nY ==nEndY ) - { - nLineStart = pMapIY[ nY ]; - nLineRange = 0; - } - else - { - nLineStart = pMapIY[ nTop ] ; - nLineRange = ( pMapIY[ nBottom ] == pMapIY[ nTop ] ) ? 1 :( pMapIY[ nBottom ] - pMapIY[ nTop ] ); - } - - for( long nX = nStartX , nXDst = 0L; nX <= nEndX; nX++ ) - { - long nLeft = bHMirr ? ( nX + 1 ) : nX; - long nRight = bHMirr ? nX : ( nX + 1 ) ; - - long nRowStart, nRowRange; - if( nX == nEndX ) - { - nRowStart = pMapIX[ nX ]; - nRowRange = 0; - } - else - { - nRowStart = pMapIX[ nLeft ]; - nRowRange = ( pMapIX[ nRight ] == pMapIX[ nLeft ] )? 1 : ( pMapIX[ nRight ] - pMapIX[ nLeft ] ); - } - - long nSumR = 0; - long nSumG = 0; - long nSumB = 0; - long nTotalWeightY = 0; - - for(int i = 0; i<= nLineRange; i++) - { - Scanline pTmpY = pAcc->GetScanline( nLineStart + i ); - Scanline pTmpX = pTmpY + 3L * nRowStart; - long nSumRowR = 0; - long nSumRowG = 0; - long nSumRowB = 0; - long nTotalWeightX = 0; - - for(int j = 0; j <= nRowRange; j++) - { - if(nX == nEndX ) - { - nSumRowR += ( *pTmpX ) << 7L;pTmpX++; - nSumRowG += ( *pTmpX ) << 7L;pTmpX++; - nSumRowB += ( *pTmpX ) << 7L;pTmpX++; - nTotalWeightX += 1 << 7L; - } - else if( j == 0 ) - { - long nWeightX = (nMax- pMapFX[ nLeft ]) ; - nSumRowR += ( nWeightX *( *pTmpX )) ;pTmpX++; - nSumRowG += ( nWeightX *( *pTmpX )) ;pTmpX++; - nSumRowB += ( nWeightX *( *pTmpX )) ;pTmpX++; - nTotalWeightX += nWeightX; - } - else if ( nRowRange == j ) - { - long nWeightX = pMapFX[ nRight ] ; - nSumRowR += ( nWeightX *( *pTmpX ) );pTmpX++; - nSumRowG += ( nWeightX *( *pTmpX ) );pTmpX++; - nSumRowB += ( nWeightX *( *pTmpX ) );pTmpX++; - nTotalWeightX += nWeightX; - } - else - { - nSumRowR += ( *pTmpX ) << 7L;pTmpX++; - nSumRowG += ( *pTmpX ) << 7L;pTmpX++; - nSumRowB += ( *pTmpX ) << 7L;pTmpX++; - nTotalWeightX += 1 << 7L; - } - } - - long nWeightY = nMax; - if( nY == nEndY ) - nWeightY = nMax; - else if( i == 0 ) - nWeightY = nMax - pMapFY[ nTop ]; - else if( nLineRange == 1 ) - nWeightY = pMapFY[ nTop ]; - else if ( nLineRange == i ) - nWeightY = pMapFY[ nBottom ]; - - nSumB += nWeightY * ( nSumRowB / nTotalWeightX ); - nSumG += nWeightY * ( nSumRowG / nTotalWeightX ); - nSumR += nWeightY * ( nSumRowR / nTotalWeightX ); - nTotalWeightY += nWeightY; - } - - BitmapColor aColRes( ( sal_uInt8 ) (( nSumR / nTotalWeightY ) ), - ( sal_uInt8 ) (( nSumG / nTotalWeightY) ), - ( sal_uInt8 ) (( nSumB / nTotalWeightY) )); - pWAcc->SetPixel( nYDst, nXDst++, aColRes ); - } - } - } - } - else - { - if( scaleX >= fScaleThresh && scaleY >= fScaleThresh ) - { - for( long nY = nStartY, nYDst = 0L; nY <= nEndY; nY++, nYDst++ ) - { - long nTempY = pMapIY[ nY ]; - long nTempFY = pMapFY[ nY ]; - - for( long nX = nStartX, nXDst = 0L; nX <= nEndX; nX++ ) - { - long nTempX = pMapIX[ nX ]; - long nTempFX = pMapFX[ nX ]; - - BitmapColor aCol0 = pAcc->GetPixel( nTempY, nTempX ); - BitmapColor aCol1 = pAcc->GetPixel( nTempY, ++nTempX ); - sal_uInt8 cR0 = MAP( aCol0.GetRed(), aCol1.GetRed(), nTempFX ); - sal_uInt8 cG0 = MAP( aCol0.GetGreen(), aCol1.GetGreen(), nTempFX ); - sal_uInt8 cB0 = MAP( aCol0.GetBlue(), aCol1.GetBlue(), nTempFX ); - - aCol1 = pAcc->GetPixel( ++nTempY, nTempX ); - aCol0 = pAcc->GetPixel( nTempY--, --nTempX ); - sal_uInt8 cR1 = MAP( aCol0.GetRed(), aCol1.GetRed(), nTempFX ); - sal_uInt8 cG1 = MAP( aCol0.GetGreen(), aCol1.GetGreen(), nTempFX ); - sal_uInt8 cB1 = MAP( aCol0.GetBlue(), aCol1.GetBlue(), nTempFX ); - - BitmapColor aColRes( MAP( cR0, cR1, nTempFY ), - MAP( cG0, cG1, nTempFY ), - MAP( cB0, cB1, nTempFY ) ); - pWAcc->SetPixel( nYDst, nXDst++, aColRes ); - } - } - } - else - { - for( long nY = nStartY , nYDst = 0L; nY <= nEndY; nY++, nYDst++ ) - { - long nTop = bVMirr ? ( nY + 1 ) : nY; - long nBottom = bVMirr ? nY : ( nY + 1 ) ; - - long nLineStart, nLineRange; - if( nY ==nEndY ) - { - nLineStart = pMapIY[ nY ]; - nLineRange = 0; - } - else - { - nLineStart = pMapIY[ nTop ] ; - nLineRange = ( pMapIY[ nBottom ] == pMapIY[ nTop ] ) ? 1 :( pMapIY[ nBottom ] - pMapIY[ nTop ] ); - } - - for( long nX = nStartX , nXDst = 0L; nX <= nEndX; nX++ ) - { - long nLeft = bHMirr ? ( nX + 1 ) : nX; - long nRight = bHMirr ? nX : ( nX + 1 ) ; - - long nRowStart, nRowRange; - if( nX == nEndX ) - { - nRowStart = pMapIX[ nX ]; - nRowRange = 0; - } - else - { - nRowStart = pMapIX[ nLeft ]; - nRowRange = ( pMapIX[ nRight ] == pMapIX[ nLeft ] )? 1 : ( pMapIX[ nRight ] - pMapIX[ nLeft ] ); - } - - long nSumR = 0; - long nSumG = 0; - long nSumB = 0; - long nTotalWeightY = 0; - - for(int i = 0; i<= nLineRange; i++) - { - long nSumRowR = 0; - long nSumRowG = 0; - long nSumRowB = 0; - long nTotalWeightX = 0; - - for(int j = 0; j <= nRowRange; j++) - { - BitmapColor aCol0 = pAcc->GetPixel( nLineStart + i, nRowStart + j ); - - if(nX == nEndX ) - { - - nSumRowB += aCol0.GetBlue() << 7L; - nSumRowG += aCol0.GetGreen() << 7L; - nSumRowR += aCol0.GetRed() << 7L; - nTotalWeightX += 1 << 7L; - } - else if( j == 0 ) - { - - long nWeightX = (nMax- pMapFX[ nLeft ]) ; - nSumRowB += ( nWeightX *aCol0.GetBlue()) ; - nSumRowG += ( nWeightX *aCol0.GetGreen()) ; - nSumRowR += ( nWeightX *aCol0.GetRed()) ; - nTotalWeightX += nWeightX; - } - else if ( nRowRange == j ) - { - - long nWeightX = pMapFX[ nRight ] ; - nSumRowB += ( nWeightX *aCol0.GetBlue() ); - nSumRowG += ( nWeightX *aCol0.GetGreen() ); - nSumRowR += ( nWeightX *aCol0.GetRed() ); - nTotalWeightX += nWeightX; - } - else - { - nSumRowB += aCol0.GetBlue() << 7L; - nSumRowG += aCol0.GetGreen() << 7L; - nSumRowR += aCol0.GetRed() << 7L; - nTotalWeightX += 1 << 7L; - } - } - - long nWeightY = nMax; - if( nY == nEndY ) - nWeightY = nMax; - else if( i == 0 ) - nWeightY = nMax - pMapFY[ nTop ]; - else if( nLineRange == 1 ) - nWeightY = pMapFY[ nTop ]; - else if ( nLineRange == i ) - nWeightY = pMapFY[ nBottom ]; - - nSumB += nWeightY * ( nSumRowB / nTotalWeightX ); - nSumG += nWeightY * ( nSumRowG / nTotalWeightX ); - nSumR += nWeightY * ( nSumRowR / nTotalWeightX ); - nTotalWeightY += nWeightY; - } - - BitmapColor aColRes( ( sal_uInt8 ) (( nSumR / nTotalWeightY) ), - ( sal_uInt8 ) (( nSumG / nTotalWeightY) ), - ( sal_uInt8 ) (( nSumB / nTotalWeightY) )); - pWAcc->SetPixel( nYDst, nXDst++, aColRes ); - - } - } - } - } - } - - bRet = true; - } - - if( bRet ) - { - ImplAdaptBitCount(aOutBmp); - ImplAssignWithSize(aOutBmp); - } - - if( !bRet ) - bRet = ImplScaleFast( scaleX, scaleY ); - } - - return bRet; -} - namespace { void ImplCalculateContributions( |