38 Qgis::RasterBandStatistics stats,
40 int sampleSize )
const
42 QgsDebugMsgLevel( QStringLiteral(
"theBandNo = %1 sampleSize = %2" ).arg( bandNo ).arg( sampleSize ), 4 );
56 statistics.
extent = finalExtent;
62 xRes = yRes = std::sqrt( ( finalExtent.
width() * finalExtent.
height() ) / sampleSize );
69 if ( xRes < srcXRes ) xRes = srcXRes;
70 if ( yRes < srcYRes ) yRes = srcYRes;
72 QgsDebugMsgLevel( QStringLiteral(
"xRes = %1 yRes = %2" ).arg( xRes ).arg( yRes ), 4 );
74 statistics.
width =
static_cast <int>( std::ceil( finalExtent.
width() / xRes ) );
75 statistics.
height =
static_cast <int>( std::ceil( finalExtent.
height() / yRes ) );
86 statistics.
width = 1000;
90 QgsDebugMsgLevel( QStringLiteral(
"theStatistics.width = %1 statistics.height = %2" ).arg( statistics.
width ).arg( statistics.
height ), 4 );
94 Qgis::RasterBandStatistics stats,
98 QgsDebugMsgLevel( QStringLiteral(
"theBandNo = %1 stats = %2 sampleSize = %3" ).arg( bandNo ).arg( stats ).arg( sampleSize ), 4 );
107 if ( stats.contains( myRasterBandStats ) )
117 Qgis::RasterBandStatistics stats,
121 QgsDebugMsgLevel( QStringLiteral(
"theBandNo = %1 stats = %2 sampleSize = %3" ).arg( bandNo ).arg( stats ).arg( sampleSize ), 4 );
131 if ( stats.contains( myRasterBandStats ) )
139 const int myWidth = myRasterBandStats.
width;
140 const int myHeight = myRasterBandStats.
height;
146 if ( myXBlockSize == 0 )
150 if ( myYBlockSize == 0 )
155 const int myNXBlocks = ( myWidth + myXBlockSize - 1 ) / myXBlockSize;
156 const int myNYBlocks = ( myHeight + myYBlockSize - 1 ) / myYBlockSize;
158 const double myXRes = myExtent.
width() / myWidth;
159 const double myYRes = myExtent.
height() / myHeight;
164 double mySumOfSquares = 0;
166 bool myFirstIterationFlag =
true;
167 bool isNoData =
false;
168 for (
int myYBlock = 0; myYBlock < myNYBlocks; myYBlock++ )
170 for (
int myXBlock = 0; myXBlock < myNXBlocks; myXBlock++ )
173 return myRasterBandStats;
175 QgsDebugMsgLevel( QStringLiteral(
"myYBlock = %1 myXBlock = %2" ).arg( myYBlock ).arg( myXBlock ), 4 );
176 const int myBlockWidth = std::min( myXBlockSize, myWidth - myXBlock * myXBlockSize );
177 const int myBlockHeight = std::min( myYBlockSize, myHeight - myYBlock * myYBlockSize );
179 const double xmin = myExtent.
xMinimum() + myXBlock * myXBlockSize * myXRes;
180 const double xmax = xmin + myBlockWidth * myXRes;
181 const double ymin = myExtent.
yMaximum() - myYBlock * myYBlockSize * myYRes;
182 const double ymax = ymin - myBlockHeight * myYRes;
184 const QgsRectangle myPartExtent( xmin, ymin, xmax, ymax );
186 std::unique_ptr< QgsRasterBlock > blk(
block( bandNo, myPartExtent, myBlockWidth, myBlockHeight, feedback ) );
189 for (
qgssize i = 0; i < ( static_cast< qgssize >( myBlockHeight ) ) * myBlockWidth; i++ )
191 const double myValue = blk->valueAndNoData( i, isNoData );
195 myRasterBandStats.
sum += myValue;
198 if ( !std::isfinite( myValue ) )
continue;
200 if ( myFirstIterationFlag )
202 myFirstIterationFlag =
false;
219 const double myDelta = myValue - myMean;
221 mySumOfSquares += myDelta * ( myValue - myMean );
234 myRasterBandStats.
stdDev = std::sqrt( mySumOfSquares / ( myRasterBandStats.
elementCount - 1 ) );
236 QgsDebugMsgLevel( QStringLiteral(
"************ STATS **************" ), 4 );
246 return myRasterBandStats;
251 return hasStatistics( bandNo,
static_cast< Qgis::RasterBandStatistics
>( stats ),
extent, sampleSize );
257 double minimum,
double maximum,
260 bool includeOutOfRange )
310 if ( sampleSize > 0 )
314 xRes = yRes = std::sqrt( (
static_cast<double>( finalExtent.
width( ) ) * finalExtent.
height() ) / sampleSize );
321 if ( xRes < srcXRes ) xRes = srcXRes;
322 if ( yRes < srcYRes ) yRes = srcYRes;
324 QgsDebugMsgLevel( QStringLiteral(
"xRes = %1 yRes = %2" ).arg( xRes ).arg( yRes ), 4 );
344 qint64 myBinCount = binCount;
345 if ( myBinCount == 0 )
383 initStatistics( statistics, bandNo,
static_cast< Qgis::RasterBandStatistics
>( stats ), boundingBox, binCount );
388 double minimum,
double maximum,
391 bool includeOutOfRange )
393 QgsDebugMsgLevel( QStringLiteral(
"theBandNo = %1 binCount = %2 minimum = %3 maximum = %4 sampleSize = %5" ).arg( bandNo ).arg( binCount ).arg( minimum ).arg( maximum ).arg( sampleSize ), 4 );
399 initHistogram( myHistogram, bandNo, binCount, minimum, maximum,
extent, sampleSize, includeOutOfRange );
415 double minimum,
double maximum,
420 QgsDebugMsgLevel( QStringLiteral(
"theBandNo = %1 binCount = %2 minimum = %3 maximum = %4 sampleSize = %5" ).arg( bandNo ).arg( binCount ).arg( minimum ).arg( maximum ).arg( sampleSize ), 4 );
423 initHistogram( myHistogram, bandNo, binCount, minimum, maximum,
extent, sampleSize, includeOutOfRange );
436 const int myBinCount = myHistogram.
binCount;
437 const int myWidth = myHistogram.
width;
438 const int myHeight = myHistogram.
height;
444 if ( myXBlockSize == 0 )
448 if ( myYBlockSize == 0 )
453 const int myNXBlocks = ( myWidth + myXBlockSize - 1 ) / myXBlockSize;
454 const int myNYBlocks = ( myHeight + myYBlockSize - 1 ) / myYBlockSize;
456 const double myXRes = myExtent.
width() / myWidth;
457 const double myYRes = myExtent.
height() / myHeight;
459 double myMinimum = myHistogram.
minimum;
460 double myMaximum = myHistogram.
maximum;
464 const double myerval = ( myMaximum - myMinimum ) / myHistogram.
binCount;
465 myMinimum -= 0.1 * myerval;
466 myMaximum += 0.1 * myerval;
468 QgsDebugMsgLevel( QStringLiteral(
"binCount = %1 myMinimum = %2 myMaximum = %3" ).arg( myHistogram.
binCount ).arg( myMinimum ).arg( myMaximum ), 4 );
470 const double myBinSize = ( myMaximum - myMinimum ) / myBinCount;
473 bool isNoData =
false;
474 for (
int myYBlock = 0; myYBlock < myNYBlocks; myYBlock++ )
476 for (
int myXBlock = 0; myXBlock < myNXBlocks; myXBlock++ )
481 const int myBlockWidth = std::min( myXBlockSize, myWidth - myXBlock * myXBlockSize );
482 const int myBlockHeight = std::min( myYBlockSize, myHeight - myYBlock * myYBlockSize );
484 const double xmin = myExtent.
xMinimum() + myXBlock * myXBlockSize * myXRes;
485 const double xmax = xmin + myBlockWidth * myXRes;
486 const double ymin = myExtent.
yMaximum() - myYBlock * myYBlockSize * myYRes;
487 const double ymax = ymin - myBlockHeight * myYRes;
489 const QgsRectangle myPartExtent( xmin, ymin, xmax, ymax );
491 std::unique_ptr< QgsRasterBlock > blk(
block( bandNo, myPartExtent, myBlockWidth, myBlockHeight, feedback ) );
494 for (
qgssize i = 0; i < ( static_cast< qgssize >( myBlockHeight ) ) * myBlockWidth; i++ )
496 const double myValue = blk->valueAndNoData( i, isNoData );
502 int myBinIndex =
static_cast <int>( std::floor( ( myValue - myMinimum ) / myBinSize ) );
504 if ( ( myBinIndex < 0 || myBinIndex > ( myBinCount - 1 ) ) && !includeOutOfRange )
508 if ( myBinIndex < 0 ) myBinIndex = 0;
509 if ( myBinIndex > ( myBinCount - 1 ) ) myBinIndex = myBinCount - 1;
517 myHistogram.
valid =
true;
522 for ( std::size_t i = 0; i < std::min< std::size_t >( myHistogram.
histogramVector.size(), 500 ); i++ )
524 hist += QString::number( myHistogram.
histogramVector.value( i ) ) +
' ';
526 QgsDebugMsgLevel( QStringLiteral(
"Histogram (max first 500 bins): " ) + hist, 4 );
533 double lowerCount,
double upperCount,
534 double &lowerValue,
double &upperValue,
538 QgsDebugMsgLevel( QStringLiteral(
"theBandNo = %1 lowerCount = %2 upperCount = %3 sampleSize = %4" ).arg( bandNo ).arg( lowerCount ).arg( upperCount ).arg( sampleSize ), 4 );
543 lowerValue = std::numeric_limits<double>::quiet_NaN();
544 upperValue = std::numeric_limits<double>::quiet_NaN();
558 const int myMinCount =
static_cast< int >( std::round( lowerCount * myHistogram.
nonNullCount ) );
559 const int myMaxCount =
static_cast< int >( std::round( upperCount * myHistogram.
nonNullCount ) );
560 bool myLowerFound =
false;
561 QgsDebugMsgLevel( QStringLiteral(
"binCount = %1 minimum = %2 maximum = %3 myBinXStep = %4" ).arg( myHistogram.
binCount ).arg( myHistogram.
minimum ).arg( myHistogram.
maximum ).arg( myBinXStep ), 4 );
562 QgsDebugMsgLevel( QStringLiteral(
"myMinCount = %1 myMaxCount = %2" ).arg( myMinCount ).arg( myMaxCount ), 4 );
564 for (
int myBin = 0; myBin < myHistogram.
histogramVector.size(); myBin++ )
567 myCount += myBinValue;
568 if ( !myLowerFound && myCount > myMinCount )
570 lowerValue = myHistogram.
minimum + myBin * myBinXStep;
572 QgsDebugMsgLevel( QStringLiteral(
"found lowerValue %1 at bin %2" ).arg( lowerValue ).arg( myBin ), 4 );
574 if ( myCount >= myMaxCount )
576 upperValue = myHistogram.
minimum + myBin * myBinXStep;
577 QgsDebugMsgLevel( QStringLiteral(
"found upperValue %1 at bin %2" ).arg( upperValue ).arg( myBin ), 4 );
587 if ( !std::isnan( lowerValue ) )
588 lowerValue = std::floor( lowerValue );
589 if ( !std::isnan( upperValue ) )
590 upperValue = std::ceil( upperValue );
596 QStringList abilitiesList;
606 abilitiesList += tr(
"Identify" );
611 abilitiesList += tr(
"Create Datasources" );
616 abilitiesList += tr(
"Remove Datasources" );
621 abilitiesList += tr(
"Build Pyramids" );
624 QgsDebugMsgLevel(
"Capability: " + abilitiesList.join( QLatin1String(
", " ) ), 4 );
626 return abilitiesList.join( QLatin1String(
", " ) );
635 return tr(
"Band" ) + QStringLiteral(
" %1" ) .arg( bandNumber, 1 + (
bandCount() > 0 ?
static_cast< int >( std::log10(
static_cast< double >(
bandCount() ) ) ) : 0 ), 10, QChar(
'0' ) );
650 if ( colorInterp != QLatin1String(
"Undefined" ) )
652 name.append( QStringLiteral(
" (%1)" ).arg( colorInterp ) );
659 return bandStatistics( bandNo,
static_cast < Qgis::RasterBandStatistics
>( stats ),
extent, sampleSize, feedback );
664 return mRenderContext;
@ All
All available statistics.
DataType
Raster data types.
@ Int16
Sixteen bit signed integer (qint16)
@ UInt16
Sixteen bit unsigned integer (quint16)
@ Byte
Eight bit unsigned integer (quint8)
@ Int32
Thirty two bit signed integer (qint32)
@ UInt32
Thirty two bit unsigned integer (quint32)
bool isCanceled() const
Tells whether the operation has been canceled already.
The RasterBandStats struct is a container for statistics about a single raster band.
qgssize elementCount
The number of not no data cells in the band.
int bandNumber
The gdal band number (starts at 1)
double sumOfSquares
The sum of the squares. Used to calculate standard deviation.
int height
Number of rows used to calc statistics.
double mean
The mean cell value for the band. NO_DATA values are excluded.
QgsRectangle extent
Extent used to calc statistics.
double stdDev
The standard deviation of the cell values.
double minimumValue
The minimum cell value in the raster band.
int width
Number of columns used to calc statistics.
double sum
The sum of all cells in the band. NO_DATA values are excluded.
Qgis::RasterBandStatistics statsGathered
Collected statistics.
double maximumValue
The maximum cell value in the raster band.
double range
The range is the distance between min & max.
Feedback object tailored for raster block reading.
QgsRenderContext renderContext() const
Returns the render context of the associated block reading.
void setRenderContext(const QgsRenderContext &renderContext)
Sets the render context of the associated block reading.
The QgsRasterHistogram is a container for histogram of a single raster band.
double minimum
The minimum histogram value.
int bandNumber
The gdal band number (starts at 1)
double maximum
The maximum histogram value.
bool includeOutOfRange
Whether histogram includes out of range values (in first and last bin)
QgsRectangle extent
Extent used to calc histogram.
int nonNullCount
The number of non NULL cells used to calculate histogram.
QgsRasterHistogram::HistogramVector histogramVector
Stores the histogram for a given layer.
int height
Number of rows used to calc histogram.
int width
Number of columns used to calc histogram.
bool valid
Histogram is valid.
int binCount
Number of bins (intervals,buckets) in histogram.
Base class for processing filters like renderers, reprojector, resampler etc.
virtual void cumulativeCut(int bandNo, double lowerCount, double upperCount, double &lowerValue, double &upperValue, const QgsRectangle &extent=QgsRectangle(), int sampleSize=0)
Find values for cumulative pixel count cut.
virtual int yBlockSize() const
virtual QgsRasterBlock * block(int bandNo, const QgsRectangle &extent, int width, int height, QgsRasterBlockFeedback *feedback=nullptr)=0
Read block of data using given extent and size.
Q_DECL_DEPRECATED void initStatistics(QgsRasterBandStats &statistics, int bandNo, int stats, const QgsRectangle &boundingBox=QgsRectangle(), int binCount=0) const
Fill in statistics defaults if not specified.
QList< QgsRasterBandStats > mStatistics
List of cached statistics, all bands mixed.
QString capabilitiesString() const
Returns the raster interface capabilities in friendly format.
@ BuildPyramids
Supports building of pyramids (overviews)
@ Identify
At least one identify format supported.
@ Create
Create new datasets.
@ Size
Original data source size (and thus resolution) is known, it is not always available,...
void initHistogram(QgsRasterHistogram &histogram, int bandNo, int binCount, double minimum=std::numeric_limits< double >::quiet_NaN(), double maximum=std::numeric_limits< double >::quiet_NaN(), const QgsRectangle &boundingBox=QgsRectangle(), int sampleSize=0, bool includeOutOfRange=false)
Fill in histogram defaults if not specified.
virtual int xSize() const
Gets raster size.
virtual QString generateBandName(int bandNumber) const
helper function to create zero padded band names
QgsRasterInterface(QgsRasterInterface *input=nullptr)
Q_DECL_DEPRECATED QgsRasterBandStats bandStatistics(int bandNo, int stats, const QgsRectangle &extent=QgsRectangle(), int sampleSize=0, QgsRasterBlockFeedback *feedback=nullptr)
Returns the band statistics.
virtual Qgis::DataType sourceDataType(int bandNo) const
Returns source data type for the band specified by number, source data type may be shorter than dataT...
virtual int xBlockSize() const
Gets block size.
virtual int bandCount() const =0
Gets number of bands.
virtual bool hasHistogram(int bandNo, int binCount, double minimum=std::numeric_limits< double >::quiet_NaN(), double maximum=std::numeric_limits< double >::quiet_NaN(), const QgsRectangle &extent=QgsRectangle(), int sampleSize=0, bool includeOutOfRange=false)
Returns true if histogram is available (cached, already calculated)
QString displayBandName(int bandNumber) const
Generates a friendly, descriptive name for the specified bandNumber.
Q_DECL_DEPRECATED bool hasStatistics(int bandNo, int stats, const QgsRectangle &extent=QgsRectangle(), int sampleSize=0)
Returns true if histogram is available (cached, already calculated).
QgsRasterInterface * mInput
virtual int capabilities() const
Returns a bitmask containing the supported capabilities.
virtual int ySize() const
virtual QgsRectangle extent() const
Gets the extent of the interface.
QList< QgsRasterHistogram > mHistograms
List of cached histograms, all bands mixed.
virtual QString colorInterpretationName(int bandNumber) const
Returns the name of the color interpretation for the specified bandNumber.
virtual QgsRasterHistogram histogram(int bandNo, int binCount=0, double minimum=std::numeric_limits< double >::quiet_NaN(), double maximum=std::numeric_limits< double >::quiet_NaN(), const QgsRectangle &extent=QgsRectangle(), int sampleSize=0, bool includeOutOfRange=false, QgsRasterBlockFeedback *feedback=nullptr)
Returns a band histogram.
A rectangle specified with double values.
double xMinimum() const
Returns the x minimum value (left side of rectangle).
double width() const
Returns the width of the rectangle.
double yMaximum() const
Returns the y maximum value (top side of rectangle).
bool isEmpty() const
Returns true if the rectangle has no area.
double height() const
Returns the height of the rectangle.
QgsRectangle intersect(const QgsRectangle &rect) const
Returns the intersection with the given rectangle.
Contains information about the context of a rendering operation.
unsigned long long qgssize
Qgssize is used instead of size_t, because size_t is stdlib type, unknown by SIP, and it would be har...
#define QgsDebugMsgLevel(str, level)