diff --git a/src/core/raster/qgsmultibandcolorrenderer.cpp b/src/core/raster/qgsmultibandcolorrenderer.cpp index 17257c8937b1..8eb08edaa402 100644 --- a/src/core/raster/qgsmultibandcolorrenderer.cpp +++ b/src/core/raster/qgsmultibandcolorrenderer.cpp @@ -49,7 +49,7 @@ void QgsMultiBandColorRenderer::draw( QPainter* p, QgsRasterViewPort* viewPort, transparencyType = ( QgsRasterDataProvider::DataType )mProvider->dataType( mAlphaBand ); } - double oversampling; + double oversamplingX, oversamplingY; QSet bands; bands << mRedBand << mGreenBand << mBlueBand; if ( mAlphaBand > 0 ) @@ -63,7 +63,7 @@ void QgsMultiBandColorRenderer::draw( QPainter* p, QgsRasterViewPort* viewPort, for ( ; bandIt != bands.constEnd(); ++bandIt ) { bandData.insert( *bandIt, defaultPointer ); - startRasterRead( *bandIt, viewPort, theQgsMapToPixel, oversampling ); + startRasterRead( *bandIt, viewPort, theQgsMapToPixel, oversamplingX, oversamplingY ); } void* redData; @@ -135,11 +135,11 @@ void QgsMultiBandColorRenderer::draw( QPainter* p, QgsRasterViewPort* viewPort, //draw image //top left position in device coords QPointF tlPoint = QPointF( viewPort->topLeftPoint.x(), viewPort->topLeftPoint.y() ); - tlPoint += QPointF( topLeftCol / oversampling, topLeftRow / oversampling ); + tlPoint += QPointF( topLeftCol / oversamplingX, topLeftRow / oversamplingY ); if ( mResampler ) //resample to output resolution { - QImage dstImg( nCols / oversampling + 0.5, nRows / oversampling + 0.5, QImage::Format_ARGB32_Premultiplied ); + QImage dstImg( nCols / oversamplingX, nRows / oversamplingY, QImage::Format_ARGB32_Premultiplied ); mResampler->resample( img, dstImg ); p->drawImage( tlPoint, dstImg ); } diff --git a/src/core/raster/qgspalettedrasterrenderer.cpp b/src/core/raster/qgspalettedrasterrenderer.cpp index 7de8c83e98bf..73d2aa40a981 100644 --- a/src/core/raster/qgspalettedrasterrenderer.cpp +++ b/src/core/raster/qgspalettedrasterrenderer.cpp @@ -43,18 +43,18 @@ void QgsPalettedRasterRenderer::draw( QPainter* p, QgsRasterViewPort* viewPort, return; } - double oversampling; + double oversamplingX, oversamplingY; QgsRasterDataProvider::DataType transparencyType; if ( mAlphaBand > 0 ) { transparencyType = ( QgsRasterDataProvider::DataType )mProvider->dataType( mAlphaBand ); } - startRasterRead( mBandNumber, viewPort, theQgsMapToPixel, oversampling ); + startRasterRead( mBandNumber, viewPort, theQgsMapToPixel, oversamplingX, oversamplingY ); //Read alpha band if necessary if ( mAlphaBand > 0 && mAlphaBand != mBandNumber ) { - startRasterRead( mAlphaBand, viewPort, theQgsMapToPixel, oversampling ); + startRasterRead( mAlphaBand, viewPort, theQgsMapToPixel, oversamplingX, oversamplingY ); } int nCols = 0; @@ -116,12 +116,12 @@ void QgsPalettedRasterRenderer::draw( QPainter* p, QgsRasterViewPort* viewPort, //top left position in device coords QPointF tlPoint = QPointF( viewPort->topLeftPoint.x(), viewPort->topLeftPoint.y() ); - tlPoint += QPointF( topLeftCol / oversampling, topLeftRow / oversampling ); + tlPoint += QPointF( topLeftCol / oversamplingX, topLeftRow / oversamplingY ); //draw image if ( mResampler ) //resample to output resolution { - QImage dstImg( nCols / oversampling, nRows / oversampling, QImage::Format_ARGB32_Premultiplied ); + QImage dstImg( nCols / oversamplingX, nRows / oversamplingY, QImage::Format_ARGB32_Premultiplied ); mResampler->resample( img, dstImg ); p->drawImage( tlPoint, dstImg ); } diff --git a/src/core/raster/qgsrasterrenderer.cpp b/src/core/raster/qgsrasterrenderer.cpp index abccea7c7655..5f0068a3b9a4 100644 --- a/src/core/raster/qgsrasterrenderer.cpp +++ b/src/core/raster/qgsrasterrenderer.cpp @@ -21,7 +21,7 @@ #include "qgsmaptopixel.h" QgsRasterRenderer::QgsRasterRenderer( QgsRasterDataProvider* provider, QgsRasterResampler* resampler ): mProvider( provider ), mResampler( resampler ), - mOpacity( 1.0 ), mRasterTransparency( 0 ), mAlphaBand( -1 ), mInvertColor( false ) + mOpacity( 1.0 ), mRasterTransparency( 0 ), mAlphaBand( -1 ), mInvertColor( false ) { } @@ -35,9 +35,8 @@ QgsRasterRenderer::~QgsRasterRenderer() } } -void QgsRasterRenderer::startRasterRead( int bandNumber, QgsRasterViewPort* viewPort, const QgsMapToPixel* mapToPixel, double& oversampling ) +void QgsRasterRenderer::startRasterRead( int bandNumber, QgsRasterViewPort* viewPort, const QgsMapToPixel* mapToPixel, double& oversamplingX, double& oversamplingY ) { - oversampling = 1.0; //default (e.g. for nearest neighbour) if ( !viewPort || !mapToPixel || !mProvider ) { return; @@ -47,6 +46,7 @@ void QgsRasterRenderer::startRasterRead( int bandNumber, QgsRasterViewPort* view removePartInfo( bandNumber ); //calculate oversampling factor + double oversampling = 1.0; //approximate global oversampling factor if ( mResampler ) { QgsRectangle providerExtent = mProvider->extent(); @@ -63,11 +63,16 @@ void QgsRasterRenderer::startRasterRead( int bandNumber, QgsRasterViewPort* view RasterPartInfo pInfo; pInfo.nCols = viewPort->drawableAreaXDim * oversampling; pInfo.nRows = viewPort->drawableAreaYDim * oversampling; + + //effective oversampling factors are different to global one because of rounding + oversamplingX = ( double )pInfo.nCols / viewPort->drawableAreaXDim; + oversamplingY = ( double )pInfo.nRows / viewPort->drawableAreaYDim; + int totalMemoryUsage = pInfo.nCols * pInfo.nRows * mProvider->dataTypeSize( bandNumber ); - int parts = totalMemoryUsage / 100000000 /*100000*/ + 1; + int parts = totalMemoryUsage / 100000 + 1; pInfo.nPartsPerDimension = sqrt( parts ); - pInfo.nColsPerPart = pInfo.nCols / pInfo.nPartsPerDimension; - pInfo.nRowsPerPart = pInfo.nRows / pInfo.nPartsPerDimension; + pInfo.nColsPerPart = floor( pInfo.nCols / pInfo.nPartsPerDimension / oversamplingX ) * oversamplingX; + pInfo.nRowsPerPart = floor( pInfo.nRows / pInfo.nPartsPerDimension / oversamplingY ) * oversamplingY; pInfo.currentCol = 0; pInfo.currentRow = 0; pInfo.data = 0; diff --git a/src/core/raster/qgsrasterrenderer.h b/src/core/raster/qgsrasterrenderer.h index 15289013195c..3f8a679e8721 100644 --- a/src/core/raster/qgsrasterrenderer.h +++ b/src/core/raster/qgsrasterrenderer.h @@ -57,13 +57,13 @@ class QgsRasterRenderer void setAlphaBand( int band ) { mAlphaBand = band; } int alphaBand() const { return mAlphaBand; } - void setInvertColor( bool invert ){ mInvertColor = invert; } + void setInvertColor( bool invert ) { mInvertColor = invert; } bool invertColor() const { return mInvertColor; } protected: inline double readValue( void *data, QgsRasterDataProvider::DataType type, int index ); - void startRasterRead( int bandNumber, QgsRasterViewPort* viewPort, const QgsMapToPixel* mapToPixel, double& oversampling ); + void startRasterRead( int bandNumber, QgsRasterViewPort* viewPort, const QgsMapToPixel* mapToPixel, double& oversamplingX, double& oversamplingY ); bool readNextRasterPart( int bandNumber, QgsRasterViewPort* viewPort, int& nCols, int& nRows, void** rasterData, int& topLeftCol, int& topLeftRow ); void stopRasterRead( int bandNumber );