Add unique_ptr variant to QgsRasterIterator::readNextRasterPart

This commit is contained in:
Nyall Dawson 2018-06-11 20:11:05 +10:00
parent dc77c59a45
commit 79c907bf3e
8 changed files with 57 additions and 39 deletions

View File

@ -47,9 +47,10 @@ caller should delete the block.
:param topLeftCol: top left column
:param topLeftRow: top left row
:return: false if the last part was already returned*
:return: false if the last part was already returned
%End
void stopRasterRead( int bandNumber );
const QgsRasterInterface *input() const;

View File

@ -134,8 +134,8 @@ QVariantMap QgsRasterLayerUniqueValuesReportAlgorithm::processAlgorithm( const Q
int iterTop = 0;
int iterCols = 0;
int iterRows = 0;
QgsRasterBlock *rasterBlock = nullptr;
while ( iter.readNextRasterPart( band, iterCols, iterRows, &rasterBlock, iterLeft, iterTop ) )
std::unique_ptr< QgsRasterBlock > rasterBlock;
while ( iter.readNextRasterPart( band, iterCols, iterRows, rasterBlock, iterLeft, iterTop ) )
{
feedback->setProgress( 100 * ( ( iterTop / maxHeight * nbBlocksWidth ) + iterLeft / maxWidth ) / nbBlocks );
for ( int row = 0; row < iterRows; row++ )
@ -155,7 +155,6 @@ QVariantMap QgsRasterLayerUniqueValuesReportAlgorithm::processAlgorithm( const Q
}
}
}
delete rasterBlock;
}
QMap< double, qgssize > sortedUniqueValues;

View File

@ -72,12 +72,12 @@ void QgsRasterAnalysisUtils::statisticsFromMiddlePointTest( QgsRasterInterface *
iter.setMaximumTileHeight( maxHeight );
iter.startRasterRead( rasterBand, nCellsX, nCellsY, rasterBBox );
QgsRasterBlock *block = nullptr;
std::unique_ptr< QgsRasterBlock > block;
int iterLeft = 0;
int iterTop = 0;
int iterCols = 0;
int iterRows = 0;
while ( iter.readNextRasterPart( rasterBand, iterCols, iterRows, &block, iterLeft, iterTop ) )
while ( iter.readNextRasterPart( rasterBand, iterCols, iterRows, block, iterLeft, iterTop ) )
{
double cellCenterY = rasterBBox.yMinimum() + ( iterTop + iterRows - 0.5 ) * cellSizeY;
for ( int row = 0; row < iterRows; ++row )
@ -98,7 +98,6 @@ void QgsRasterAnalysisUtils::statisticsFromMiddlePointTest( QgsRasterInterface *
}
cellCenterY -= cellSizeY;
}
delete block;
}
}
@ -126,12 +125,12 @@ void QgsRasterAnalysisUtils::statisticsFromPreciseIntersection( QgsRasterInterfa
iter.setMaximumTileHeight( maxHeight );
iter.startRasterRead( rasterBand, nCellsX, nCellsY, rasterBBox );
QgsRasterBlock *block = nullptr;
std::unique_ptr< QgsRasterBlock > block;
int iterLeft = 0;
int iterTop = 0;
int iterCols = 0;
int iterRows = 0;
while ( iter.readNextRasterPart( rasterBand, iterCols, iterRows, &block, iterLeft, iterTop ) )
while ( iter.readNextRasterPart( rasterBand, iterCols, iterRows, block, iterLeft, iterTop ) )
{
double currentY = rasterBBox.yMinimum() + ( iterTop + iterRows - 0.5 ) * cellSizeY;
for ( int row = 0; row < iterRows; ++row )

View File

@ -48,9 +48,9 @@ void QgsReclassifyUtils::reclassify( const QVector<QgsReclassifyUtils::RasterCla
int iterCols = 0;
int iterRows = 0;
destinationRaster->setEditable( true );
QgsRasterBlock *rasterBlock = nullptr;
std::unique_ptr< QgsRasterBlock > rasterBlock;
bool reclassed = false;
while ( iter.readNextRasterPart( band, iterCols, iterRows, &rasterBlock, iterLeft, iterTop ) )
while ( iter.readNextRasterPart( band, iterCols, iterRows, rasterBlock, iterLeft, iterTop ) )
{
if ( feedback )
feedback->setProgress( 100 * ( ( iterTop / maxHeight * nbBlocksWidth ) + iterLeft / maxWidth ) / nbBlocks );
@ -76,8 +76,6 @@ void QgsReclassifyUtils::reclassify( const QVector<QgsReclassifyUtils::RasterCla
}
}
destinationRaster->writeBlock( reclassifiedBlock.get(), 1, iterLeft, iterTop );
delete rasterBlock;
}
destinationRaster->setEditable( false );
}

View File

@ -52,11 +52,11 @@ void QgsRasterDrawer::draw( QPainter *p, QgsRasterViewPort *viewPort, const QgsM
// We know that the output data type of last pipe filter is QImage data
QgsRasterBlock *block = nullptr;
std::unique_ptr< QgsRasterBlock > block;
// readNextRasterPart calcs and resets nCols, nRows, topLeftCol, topLeftRow
while ( mIterator->readNextRasterPart( bandNumber, nCols, nRows,
&block, topLeftCol, topLeftRow ) )
block, topLeftCol, topLeftRow ) )
{
if ( !block )
{
@ -100,8 +100,6 @@ void QgsRasterDrawer::draw( QPainter *p, QgsRasterViewPort *viewPort, const QgsM
drawImage( p, viewPort, img, topLeftCol, topLeftRow, qgsMapToPixel );
delete block;
if ( feedback && feedback->renderPartialOutput() )
{
// go back to the default composition mode

View File

@ -501,12 +501,11 @@ QgsRasterFileWriter::WriterError QgsRasterFileWriter::writeImageRaster( QgsRaste
int fileIndex = 0;
//create destProvider for whole dataset here
QgsRasterDataProvider *destProvider = nullptr;
double pixelSize;
double geoTransform[6];
globalOutputParameters( outputExtent, nCols, nRows, geoTransform, pixelSize );
destProvider = initOutput( nCols, nRows, crs, geoTransform, 4, Qgis::Byte );
std::unique_ptr< QgsRasterDataProvider > destProvider( initOutput( nCols, nRows, crs, geoTransform, 4, Qgis::Byte ) );
iter->startRasterRead( 1, nCols, nRows, outputExtent, feedback );
@ -518,8 +517,8 @@ QgsRasterFileWriter::WriterError QgsRasterFileWriter::writeImageRaster( QgsRaste
nParts = nPartsX * nPartsY;
}
QgsRasterBlock *inputBlock = nullptr;
while ( iter->readNextRasterPart( 1, iterCols, iterRows, &inputBlock, iterLeft, iterTop ) )
std::unique_ptr< QgsRasterBlock > inputBlock;
while ( iter->readNextRasterPart( 1, iterCols, iterRows, inputBlock, iterLeft, iterTop ) )
{
if ( !inputBlock )
{
@ -531,7 +530,6 @@ QgsRasterFileWriter::WriterError QgsRasterFileWriter::writeImageRaster( QgsRaste
feedback->setProgress( 100.0 * fileIndex / static_cast< double >( nParts ) );
if ( feedback->isCanceled() )
{
delete inputBlock;
break;
}
}
@ -564,16 +562,15 @@ QgsRasterFileWriter::WriterError QgsRasterFileWriter::writeImageRaster( QgsRaste
memcpy( reinterpret_cast< char * >( blueData ) + i, &blue, 1 );
memcpy( reinterpret_cast< char * >( alphaData ) + i, &alpha, 1 );
}
delete inputBlock;
//create output file
if ( mTiledMode )
{
//delete destProvider;
QgsRasterDataProvider *partDestProvider = createPartProvider( outputExtent,
std::unique_ptr< QgsRasterDataProvider > partDestProvider( createPartProvider( outputExtent,
nCols, iterCols, iterRows,
iterLeft, iterTop, mOutputUrl, fileIndex,
4, Qgis::Byte, crs );
4, Qgis::Byte, crs ) );
if ( partDestProvider )
{
@ -587,7 +584,6 @@ QgsRasterFileWriter::WriterError QgsRasterFileWriter::writeImageRaster( QgsRaste
addToVRT( partFileName( fileIndex ), 2, iterCols, iterRows, iterLeft, iterTop );
addToVRT( partFileName( fileIndex ), 3, iterCols, iterRows, iterLeft, iterTop );
addToVRT( partFileName( fileIndex ), 4, iterCols, iterRows, iterLeft, iterTop );
delete partDestProvider;
}
}
else if ( destProvider )
@ -600,8 +596,7 @@ QgsRasterFileWriter::WriterError QgsRasterFileWriter::writeImageRaster( QgsRaste
++fileIndex;
}
delete destProvider;
destProvider.reset();
qgsFree( redData );
qgsFree( greenData );

View File

@ -63,8 +63,18 @@ bool QgsRasterIterator::readNextRasterPart( int bandNumber,
QgsRasterBlock **block,
int &topLeftCol, int &topLeftRow )
{
QgsDebugMsgLevel( "Entered", 4 );
*block = nullptr;
std::unique_ptr< QgsRasterBlock > nextBlock;
bool result = readNextRasterPart( bandNumber, nCols, nRows, nextBlock, topLeftCol, topLeftRow );
if ( result )
*block = nextBlock.release();
return result;
}
bool QgsRasterIterator::readNextRasterPart( int bandNumber, int &nCols, int &nRows, std::unique_ptr<QgsRasterBlock> &block, int &topLeftCol, int &topLeftRow )
{
QgsDebugMsgLevel( QStringLiteral( "Entered" ), 4 );
block.reset();
//get partinfo
QMap<int, RasterPartInfo>::iterator partIt = mRasterPartInfos.find( bandNumber );
if ( partIt == mRasterPartInfos.end() )
@ -93,7 +103,7 @@ bool QgsRasterIterator::readNextRasterPart( int bandNumber,
//read data block
nCols = std::min( mMaximumTileWidth, pInfo.nCols - pInfo.currentCol );
nRows = std::min( mMaximumTileHeight, pInfo.nRows - pInfo.currentRow );
QgsDebugMsgLevel( QString( "nCols = %1 nRows = %2" ).arg( nCols ).arg( nRows ), 4 );
QgsDebugMsgLevel( QStringLiteral( "nCols = %1 nRows = %2" ).arg( nCols ).arg( nRows ), 4 );
//get subrectangle
QgsRectangle viewPortExtent = mExtent;
@ -105,7 +115,7 @@ bool QgsRasterIterator::readNextRasterPart( int bandNumber,
double ymax = viewPortExtent.yMaximum() - pInfo.currentRow / static_cast< double >( pInfo.nRows ) * viewPortExtent.height();
QgsRectangle blockRect( xmin, ymin, xmax, ymax );
*block = mInput->block( bandNumber, blockRect, nCols, nRows, mFeedback );
block.reset( mInput->block( bandNumber, blockRect, nCols, nRows, mFeedback ) );
topLeftCol = pInfo.currentCol;
topLeftRow = pInfo.currentRow;

View File

@ -48,19 +48,37 @@ class CORE_EXPORT QgsRasterIterator
/**
* Fetches next part of raster data, caller takes ownership of the block and
caller should delete the block.
\param bandNumber band to read
\param nCols number of columns on output device
\param nRows number of rows on output device
\param block address of block pointer
\param topLeftCol top left column
\param topLeftRow top left row
\returns false if the last part was already returned*/
* caller should delete the block.
* \param bandNumber band to read
* \param nCols number of columns on output device
* \param nRows number of rows on output device
* \param block address of block pointer
* \param topLeftCol top left column
* \param topLeftRow top left row
* \returns false if the last part was already returned
*/
bool readNextRasterPart( int bandNumber,
int &nCols, int &nRows,
QgsRasterBlock **block,
int &topLeftCol, int &topLeftRow );
/**
* Fetches next part of raster data.
* \param bandNumber band to read
* \param nCols number of columns on output device
* \param nRows number of rows on output device
* \param block address of block pointer
* \param topLeftCol top left column
* \param topLeftRow top left row
* \returns false if the last part was already returned
* \note Not available in Python bindings
* \since QGIS 3.2
*/
bool readNextRasterPart( int bandNumber,
int &nCols, int &nRows,
std::unique_ptr< QgsRasterBlock > &block,
int &topLeftCol, int &topLeftRow ) SIP_SKIP;
void stopRasterRead( int bandNumber );
const QgsRasterInterface *input() const { return mInput; }