Update dev branch after patch release

* Fix calculation for active cell values
Always allocate result data for active cells in destination case. Make sure that active cells is used for both population of expression variables and filtering of data. Improved naming to make it clear that we always work with active cell data.

* Check if scalar result index is valid
* Create the static scalar results once
addStaticScalarResult will clear already computed data, causing calculations to be triggered once more

* Early return if data already is available
If not checking if data is available, data is read from file and appended to result vector.

* Always check date for H5 files, and recreate if required

* Always recreate ESMRY if file exists and is older than SMSPEC

* #11355 Use category if result name starts with FIP or ends with NUM

* #11337 Summary import: Make sure ESMRY includes restart history

* #11334 Fix cvf::Viewport assert triggered for small contour map/2d intersection
Size of the overlay is could become negative, and would overflow for small views.

* #11310 Fix assert on single cell model.
Well pipe radius would become HUGE_VAL due to off-by-one error.
The assert could only happen on model with a single cell.

* Check equal grid size only when required
Equal grid size is required if there is more than one grid case in the expression. If a cell filter view is active, the visibility is based on one view and reused for all other grid models, and requires equal grid size.

* Remove obsolete log message

* Do not show dialog during regression tests

* Fix eclipse case contour map left click (#11378)

* Make sure we operate in the correct domain when picking points in the contour map

* Remove obsolete code causing grid to be loaded for all cases


* Bump version to 2024.03.1

---------

Co-authored-by: Kristian Bendiksen <kristian.bendiksen@gmail.com>
Co-authored-by: jonjenssen <69144954+jonjenssen@users.noreply.github.com>
This commit is contained in:
Magne Sjaastad
2024-04-19 15:09:15 +02:00
committed by GitHub
parent 932464ea55
commit e9ff3540ba
16 changed files with 262 additions and 150 deletions

View File

@@ -97,6 +97,17 @@ bool RiaResultNames::isFlowResultWithBothPosAndNegValues( const QString& resultN
return false; return false;
} }
//--------------------------------------------------------------------------------------------------
///
//--------------------------------------------------------------------------------------------------
bool RiaResultNames::isCategoryResult( const QString& resultName )
{
if ( resultName.endsWith( "NUM", Qt::CaseInsensitive ) ) return true;
if ( resultName.startsWith( "FIP", Qt::CaseInsensitive ) ) return true;
return false;
}
//-------------------------------------------------------------------------------------------------- //--------------------------------------------------------------------------------------------------
/// ///
//-------------------------------------------------------------------------------------------------- //--------------------------------------------------------------------------------------------------

View File

@@ -32,6 +32,7 @@ namespace RiaResultNames
bool isPerCellFaceResult( const QString& resultName ); bool isPerCellFaceResult( const QString& resultName );
bool isLogarithmicResult( const QString& resultName ); bool isLogarithmicResult( const QString& resultName );
bool isFlowResultWithBothPosAndNegValues( const QString& resultName ); bool isFlowResultWithBothPosAndNegValues( const QString& resultName );
bool isCategoryResult( const QString& resultName );
QString undefinedResultName(); QString undefinedResultName();
QString undefinedGridFaultName(); QString undefinedGridFaultName();

View File

@@ -22,6 +22,7 @@
#include "RiaCellDividingTools.h" #include "RiaCellDividingTools.h"
#include "RiaLogging.h" #include "RiaLogging.h"
#include "RiaResultNames.h"
#include "RiaStringEncodingTools.h" #include "RiaStringEncodingTools.h"
#include "RiaTextStringTools.h" #include "RiaTextStringTools.h"
@@ -439,7 +440,7 @@ bool RifEclipseInputFileTools::exportKeywords( const QString& resul
if ( resultValues.empty() ) continue; if ( resultValues.empty() ) continue;
double defaultExportValue = 0.0; double defaultExportValue = 0.0;
if ( keyword.endsWith( "NUM" ) ) if ( RiaResultNames::isCategoryResult( keyword ) )
{ {
defaultExportValue = 1.0; defaultExportValue = 1.0;
} }

View File

@@ -19,6 +19,7 @@
#include "RifEclipseInputPropertyLoader.h" #include "RifEclipseInputPropertyLoader.h"
#include "RiaLogging.h" #include "RiaLogging.h"
#include "RiaResultNames.h"
#include "RifEclipseInputFileTools.h" #include "RifEclipseInputFileTools.h"
#include "RifEclipseKeywordContent.h" #include "RifEclipseKeywordContent.h"
@@ -177,8 +178,8 @@ bool RifEclipseInputPropertyLoader::appendNewInputPropertyResult( RigEclipseCase
return false; return false;
} }
bool endsWithNum = eclipseKeyword.ends_with( "NUM" ); bool isCategory = RiaResultNames::isCategoryResult( resultName );
auto dataType = endsWithNum ? RiaDefines::ResultDataType::INTEGER : RiaDefines::ResultDataType::FLOAT; auto dataType = isCategory ? RiaDefines::ResultDataType::INTEGER : RiaDefines::ResultDataType::FLOAT;
RigEclipseResultAddress resAddr( RiaDefines::ResultCatType::INPUT_PROPERTY, dataType, resultName ); RigEclipseResultAddress resAddr( RiaDefines::ResultCatType::INPUT_PROPERTY, dataType, resultName );
caseData->results( RiaDefines::PorosityModelType::MATRIX_MODEL )->createResultEntry( resAddr, false ); caseData->results( RiaDefines::PorosityModelType::MATRIX_MODEL )->createResultEntry( resAddr, false );

View File

@@ -45,6 +45,7 @@
//-------------------------------------------------------------------------------------------------- //--------------------------------------------------------------------------------------------------
bool RifHdf5SummaryExporter::ensureHdf5FileIsCreatedMultithreaded( const std::vector<std::string>& smspecFileNames, bool RifHdf5SummaryExporter::ensureHdf5FileIsCreatedMultithreaded( const std::vector<std::string>& smspecFileNames,
const std::vector<std::string>& h5FileNames, const std::vector<std::string>& h5FileNames,
bool createHdfIfNotPresent,
int threadCount ) int threadCount )
{ {
if ( smspecFileNames.empty() ) return true; if ( smspecFileNames.empty() ) return true;
@@ -61,7 +62,7 @@ bool RifHdf5SummaryExporter::ensureHdf5FileIsCreatedMultithreaded( const std::ve
const auto& smspecFileName = smspecFileNames[cIdx]; const auto& smspecFileName = smspecFileNames[cIdx];
const auto& h5FileName = h5FileNames[cIdx]; const auto& h5FileName = h5FileNames[cIdx];
RifHdf5SummaryExporter::ensureHdf5FileIsCreated( smspecFileName, h5FileName, hdfFilesCreatedCount ); RifHdf5SummaryExporter::ensureHdf5FileIsCreated( smspecFileName, h5FileName, createHdfIfNotPresent, hdfFilesCreatedCount );
} }
if ( hdfFilesCreatedCount > 0 ) if ( hdfFilesCreatedCount > 0 )
@@ -78,30 +79,48 @@ bool RifHdf5SummaryExporter::ensureHdf5FileIsCreatedMultithreaded( const std::ve
//-------------------------------------------------------------------------------------------------- //--------------------------------------------------------------------------------------------------
/// ///
//-------------------------------------------------------------------------------------------------- //--------------------------------------------------------------------------------------------------
bool RifHdf5SummaryExporter::ensureHdf5FileIsCreated( const std::string& smspecFileName, const std::string& h5FileName, size_t& hdfFilesCreatedCount ) bool RifHdf5SummaryExporter::ensureHdf5FileIsCreated( const std::string& smspecFileName,
const std::string& h5FileName,
bool createHdfIfNotPresent,
size_t& hdfFilesCreatedCount )
{ {
// If an H5 file is present, and the SMSPEC file is newer than the H5 file, the H5 file will be recreated.
// If no H5 file is present, the H5 file will be created if the flag createHdfIfNotPresent is set to true.
//
// NB! Always make sure the logic is consistent with the logic in RifOpmCommonEclipseSummary::open
if ( !std::filesystem::exists( smspecFileName ) ) return false; if ( !std::filesystem::exists( smspecFileName ) ) return false;
{
// Check if we have write permission in the folder
QFileInfo info( QString::fromStdString( smspecFileName ) );
if ( !info.isWritable() ) return true;
}
bool exportIsRequired = false; bool exportIsRequired = false;
{
bool h5FileExists = std::filesystem::exists( h5FileName ); bool h5FileExists = std::filesystem::exists( h5FileName );
if ( !h5FileExists ) if ( !h5FileExists )
{ {
exportIsRequired = true; if ( createHdfIfNotPresent )
}
else if ( RiaFilePathTools::isFirstOlderThanSecond( h5FileName, smspecFileName ) )
{ {
exportIsRequired = true; exportIsRequired = true;
} }
} }
else if ( RiaFilePathTools::isFirstOlderThanSecond( h5FileName, smspecFileName ) )
{
// If both files are present, check if the SMSPEC file is newer than the H5 file. If the SMSPEC file is newer, we abort if it is not
// possible to write to the H5 file
// Check if we have write permission in the folder
QFileInfo info( QString::fromStdString( smspecFileName ) );
if ( !info.isWritable() )
{
QString txt =
QString( "HDF is older than SMSPEC, but export to file %1 failed due to missing write permissions. Aborting operation." )
.arg( QString::fromStdString( h5FileName ) );
RiaLogging::error( txt );
return false;
}
exportIsRequired = true;
}
if ( exportIsRequired ) if ( exportIsRequired )
{ {
@@ -127,7 +146,7 @@ bool RifHdf5SummaryExporter::ensureHdf5FileIsCreated( const std::string& smspecF
} }
catch ( std::exception& e ) catch ( std::exception& e )
{ {
QString txt = QString( "HDF export to file %1 failed : %3" ).arg( QString::fromStdString( smspecFileName ), e.what() ); QString txt = QString( "HDF export to file %1 failed : %2" ).arg( QString::fromStdString( smspecFileName ), e.what() );
RiaLogging::error( txt ); RiaLogging::error( txt );

View File

@@ -42,9 +42,13 @@ class RifHdf5SummaryExporter
public: public:
static bool ensureHdf5FileIsCreatedMultithreaded( const std::vector<std::string>& smspecFileNames, static bool ensureHdf5FileIsCreatedMultithreaded( const std::vector<std::string>& smspecFileNames,
const std::vector<std::string>& h5FileNames, const std::vector<std::string>& h5FileNames,
bool createHdfIfNotPresent,
int threadCount ); int threadCount );
static bool ensureHdf5FileIsCreated( const std::string& smspecFileName, const std::string& h5FileName, size_t& hdfFilesCreatedCount ); static bool ensureHdf5FileIsCreated( const std::string& smspecFileName,
const std::string& h5FileName,
bool createHdfIfNotPresent,
size_t& hdfFilesCreatedCount );
private: private:
static bool writeGeneralSection( RifHdf5Exporter& exporter, Opm::EclIO::ESmry& sourceSummaryData ); static bool writeGeneralSection( RifHdf5Exporter& exporter, Opm::EclIO::ESmry& sourceSummaryData );

View File

@@ -84,15 +84,24 @@ size_t RifOpmCommonEclipseSummary::numberOfEnhancedSummaryFileCreated()
//-------------------------------------------------------------------------------------------------- //--------------------------------------------------------------------------------------------------
bool RifOpmCommonEclipseSummary::open( const QString& fileName, bool includeRestartFiles, RiaThreadSafeLogger* threadSafeLogger ) bool RifOpmCommonEclipseSummary::open( const QString& fileName, bool includeRestartFiles, RiaThreadSafeLogger* threadSafeLogger )
{ {
if ( m_createEsmryFiles ) // If an ESMRY file is present, and the SMSPEC file is newer than the ESMRY file, the ESMRY file will be recreated.
{ // If no ESMRY file is present, the ESMRY file will be created if the flag m_createEsmryFiles is set to true.
//
// NB! Always make sure the logic is consistent with the logic in RifHdf5SummaryExporter::ensureHdf5FileIsCreated
bool writeDataToEsmry = false;
auto candidateEsmryFileName = enhancedSummaryFilename( fileName ); auto candidateEsmryFileName = enhancedSummaryFilename( fileName );
// Make sure to check the smspec file name, as it is supported to import ESMRY files without any SMSPEC data // Make sure to check the smspec file name, as it is supported to import ESMRY files without any SMSPEC data
auto smspecFileName = smspecSummaryFilename( fileName ); auto smspecFileName = smspecSummaryFilename( fileName );
if ( QFile::exists( candidateEsmryFileName ) && QFile::exists( smspecFileName ) && if ( !QFile::exists( candidateEsmryFileName ) && QFile::exists( smspecFileName ) && m_createEsmryFiles )
RiaFilePathTools::isFirstOlderThanSecond( candidateEsmryFileName.toStdString(), smspecFileName.toStdString() ) ) {
writeDataToEsmry = true;
}
if ( RiaFilePathTools::isFirstOlderThanSecond( candidateEsmryFileName.toStdString(), smspecFileName.toStdString() ) )
{ {
QString root = QFileInfo( smspecFileName ).canonicalPath(); QString root = QFileInfo( smspecFileName ).canonicalPath();
@@ -102,10 +111,25 @@ bool RifOpmCommonEclipseSummary::open( const QString& fileName, bool includeRest
RiaLogging::debug( RiaLogging::debug(
QString( " %3 : %1 is older than %2, recreating %1." ).arg( esmryFileNameShort ).arg( smspecFileNameShort ).arg( root ) ); QString( " %3 : %1 is older than %2, recreating %1." ).arg( esmryFileNameShort ).arg( smspecFileNameShort ).arg( root ) );
std::filesystem::remove( candidateEsmryFileName.toStdString() ); // Check if we have write permission in the folder
QFileInfo info( smspecFileName );
if ( !info.isWritable() )
{
QString txt =
QString( "ESMRY is older than SMSPEC, but export to file %1 failed due to missing write permissions. Aborting operation." )
.arg( candidateEsmryFileName );
RiaLogging::error( txt );
return false;
} }
if ( !QFile::exists( candidateEsmryFileName ) && QFile::exists( smspecFileName ) ) std::filesystem::remove( candidateEsmryFileName.toStdString() );
writeDataToEsmry = true;
}
if ( writeDataToEsmry )
{ {
try try
{ {
@@ -129,7 +153,6 @@ bool RifOpmCommonEclipseSummary::open( const QString& fileName, bool includeRest
return false; return false;
} }
} }
}
if ( !openFileReader( fileName, includeRestartFiles, threadSafeLogger ) ) return false; if ( !openFileReader( fileName, includeRestartFiles, threadSafeLogger ) ) return false;

View File

@@ -95,10 +95,11 @@ bool RifReaderEclipseSummary::open( const QString& headerFileName, RiaThreadSafe
( h5FileFound || ( prefSummary->summaryDataReader() == RiaPreferencesSummary::SummaryReaderMode::HDF5_OPM_COMMON ) ) ) ( h5FileFound || ( prefSummary->summaryDataReader() == RiaPreferencesSummary::SummaryReaderMode::HDF5_OPM_COMMON ) ) )
{ {
#ifdef USE_HDF5 #ifdef USE_HDF5
if ( prefSummary->createH5SummaryDataFiles() )
{
size_t createdH5FileCount = 0; size_t createdH5FileCount = 0;
RifHdf5SummaryExporter::ensureHdf5FileIsCreated( headerFileName.toStdString(), h5FileName.toStdString(), createdH5FileCount ); RifHdf5SummaryExporter::ensureHdf5FileIsCreated( headerFileName.toStdString(),
h5FileName.toStdString(),
prefSummary->createH5SummaryDataFiles(),
createdH5FileCount );
if ( createdH5FileCount > 0 ) if ( createdH5FileCount > 0 )
{ {
@@ -106,7 +107,6 @@ bool RifReaderEclipseSummary::open( const QString& headerFileName, RiaThreadSafe
if ( threadSafeLogger ) threadSafeLogger->info( txt ); if ( threadSafeLogger ) threadSafeLogger->info( txt );
} }
h5FileFound = QFile::exists( h5FileName ); h5FileFound = QFile::exists( h5FileName );
}
if ( h5FileFound ) if ( h5FileFound )
{ {

View File

@@ -374,8 +374,6 @@ void RimEclipseResultCase::ensureRftDataIsImported()
if ( rftFileInfo.exists() ) if ( rftFileInfo.exists() )
{ {
RiaLogging::info( QString( "RFT file found" ) );
if ( m_useOpmRftReader ) if ( m_useOpmRftReader )
{ {
m_readerOpmRft = new RifReaderOpmRft( rftFileInfo.filePath() ); m_readerOpmRft = new RifReaderOpmRft( rftFileInfo.filePath() );

View File

@@ -1426,6 +1426,8 @@ bool RimEclipseResultDefinition::isCompletionTypeSelected() const
//-------------------------------------------------------------------------------------------------- //--------------------------------------------------------------------------------------------------
bool RimEclipseResultDefinition::hasCategoryResult() const bool RimEclipseResultDefinition::hasCategoryResult() const
{ {
if ( RiaResultNames::isCategoryResult( m_resultVariable() ) ) return true;
if ( auto* gridCellResults = currentGridCellResults() ) if ( auto* gridCellResults = currentGridCellResults() )
{ {
const auto addresses = gridCellResults->existingResults(); const auto addresses = gridCellResults->existingResults();

View File

@@ -22,6 +22,7 @@
#include "RiaGuiApplication.h" #include "RiaGuiApplication.h"
#include "RiaLogging.h" #include "RiaLogging.h"
#include "RiaPorosityModel.h" #include "RiaPorosityModel.h"
#include "RiaRegressionTestRunner.h"
#include "RigActiveCellInfo.h" #include "RigActiveCellInfo.h"
#include "RigCaseCellResultsData.h" #include "RigCaseCellResultsData.h"
@@ -118,7 +119,8 @@ RimGridCalculation::RimGridCalculation()
//-------------------------------------------------------------------------------------------------- //--------------------------------------------------------------------------------------------------
bool RimGridCalculation::preCalculate() const bool RimGridCalculation::preCalculate() const
{ {
if ( RiaGuiApplication::isRunning() && m_additionalCasesType() != RimGridCalculation::AdditionalCasesType::NONE ) if ( !RiaRegressionTestRunner::instance()->isRunningRegressionTests() && RiaGuiApplication::isRunning() &&
m_additionalCasesType() != RimGridCalculation::AdditionalCasesType::NONE )
{ {
const QString cacheKey = "GridCalculatorMessage"; const QString cacheKey = "GridCalculatorMessage";
@@ -171,10 +173,31 @@ RimGridCalculationVariable* RimGridCalculation::createVariable()
//-------------------------------------------------------------------------------------------------- //--------------------------------------------------------------------------------------------------
bool RimGridCalculation::calculate() bool RimGridCalculation::calculate()
{ {
// Equal grid size is required if there is more than one grid case in the expression. If a cell filter view is active, the visibility is
// based on one view and reused for all other grid models, and requires equal grid size.
bool checkIfGridSizeIsEqual = !allSourceCasesAreEqualToDestinationCase() || m_cellFilterView != nullptr;
for ( auto calculationCase : outputEclipseCases() ) for ( auto calculationCase : outputEclipseCases() )
{ {
if ( !calculationCase ) continue; if ( !calculationCase ) continue;
if ( !calculationCase->eclipseCaseData() )
{
QString msg = QString( "No data available for case %1, aborting calculation" ).arg( calculationCase->caseUserDescription() );
RiaLogging::errorInMessageBox( nullptr, "Grid Property Calculator", msg );
return false;
}
if ( !calculationCase->eclipseCaseData()->activeCellInfo( RiaDefines::PorosityModelType::MATRIX_MODEL ) )
{
QString msg =
QString( "No active cell data available for case %1, aborting calculation" ).arg( calculationCase->caseUserDescription() );
RiaLogging::errorInMessageBox( nullptr, "Grid Property Calculator", msg );
return false;
}
if ( checkIfGridSizeIsEqual )
{
for ( auto inputCase : inputCases() ) for ( auto inputCase : inputCases() )
{ {
if ( !calculationCase->isGridSizeEqualTo( inputCase ) ) if ( !calculationCase->isGridSizeEqualTo( inputCase ) )
@@ -186,6 +209,7 @@ bool RimGridCalculation::calculate()
} }
} }
} }
}
if ( m_defaultValueType() == DefaultValueType::FROM_PROPERTY ) if ( m_defaultValueType() == DefaultValueType::FROM_PROPERTY )
{ {
@@ -537,7 +561,7 @@ RigEclipseResultAddress RimGridCalculation::outputAddress() const
//-------------------------------------------------------------------------------------------------- //--------------------------------------------------------------------------------------------------
/// ///
//-------------------------------------------------------------------------------------------------- //--------------------------------------------------------------------------------------------------
std::vector<double> RimGridCalculation::getDataForVariable( RimGridCalculationVariable* variable, std::vector<double> RimGridCalculation::getActiveCellValuesForVariable( RimGridCalculationVariable* variable,
size_t tsId, size_t tsId,
RiaDefines::PorosityModelType porosityModel, RiaDefines::PorosityModelType porosityModel,
RimEclipseCase* sourceCase, RimEclipseCase* sourceCase,
@@ -562,13 +586,14 @@ std::vector<double> RimGridCalculation::getDataForVariable( RimGridCalculationVa
timeStepToUse = timeStep; timeStepToUse = timeStep;
} }
return getDataForResult( variable->resultVariable(), resultCategoryType, timeStepToUse, porosityModel, sourceCase, destinationCase ); return getActiveCellValues( variable->resultVariable(), resultCategoryType, timeStepToUse, porosityModel, sourceCase, destinationCase );
} }
//-------------------------------------------------------------------------------------------------- //--------------------------------------------------------------------------------------------------
/// /// Return values for active cells, both for dynamic and static results. Use the active cell info from the destination case, and read data
/// from the source case.
//-------------------------------------------------------------------------------------------------- //--------------------------------------------------------------------------------------------------
std::vector<double> RimGridCalculation::getDataForResult( const QString& resultName, std::vector<double> RimGridCalculation::getActiveCellValues( const QString& resultName,
const RiaDefines::ResultCatType resultCategoryType, const RiaDefines::ResultCatType resultCategoryType,
size_t tsId, size_t tsId,
RiaDefines::PorosityModelType porosityModel, RiaDefines::PorosityModelType porosityModel,
@@ -588,12 +613,15 @@ std::vector<double> RimGridCalculation::getDataForResult( const QString&
auto eclipseCaseData = sourceCase->eclipseCaseData(); auto eclipseCaseData = sourceCase->eclipseCaseData();
auto rigCaseCellResultsData = eclipseCaseData->results( porosityModel ); auto rigCaseCellResultsData = eclipseCaseData->results( porosityModel );
if ( !rigCaseCellResultsData->findOrLoadKnownScalarResultForTimeStep( resAddr, timeStepToUse ) ) return {}; if ( rigCaseCellResultsData->findOrLoadKnownScalarResultForTimeStep( resAddr, timeStepToUse ) == cvf::UNDEFINED_SIZE_T ) return {};
// Active cell info must always be retrieved from the destination case, as the returned vector must be of the same size as // Active cell info must always be retrieved from the destination case, as the returned vector must be of the same size as
// number of active cells in the destination case. Active cells can be different between source and destination case. // number of active cells in the destination case. Active cells can be different between source and destination case.
auto activeCellInfoDestination = destinationCase->eclipseCaseData()->activeCellInfo( porosityModel ); auto activeCellInfoDestination = destinationCase->eclipseCaseData()->activeCellInfo( porosityModel );
if ( !activeCellInfoDestination ) return {};
auto activeReservoirCells = activeCellInfoDestination->activeReservoirCellIndices(); auto activeReservoirCells = activeCellInfoDestination->activeReservoirCellIndices();
if ( activeReservoirCells.empty() ) return {};
std::vector<double> values( activeCellInfoDestination->activeReservoirCellIndices().size() ); std::vector<double> values( activeCellInfoDestination->activeReservoirCellIndices().size() );
@@ -624,20 +652,22 @@ std::vector<double> RimGridCalculation::getDataForResult( const QString&
void RimGridCalculation::replaceFilteredValuesWithVector( const std::vector<double>& inputValues, void RimGridCalculation::replaceFilteredValuesWithVector( const std::vector<double>& inputValues,
cvf::ref<cvf::UByteArray> visibility, cvf::ref<cvf::UByteArray> visibility,
std::vector<double>& resultValues, std::vector<double>& resultValues,
RiaDefines::PorosityModelType porosityModel, RigActiveCellInfo* activeCellInfo )
RimEclipseCase* outputEclipseCase )
{ {
auto activeCellInfo = outputEclipseCase->eclipseCaseData()->activeCellInfo( porosityModel ); auto activeReservoirCellIndices = activeCellInfo->activeReservoirCellIndices();
int numCells = static_cast<int>( visibility->size() ); int numActiveCells = static_cast<int>( activeReservoirCellIndices.size() );
CAF_ASSERT( numActiveCells == (int)resultValues.size() );
CAF_ASSERT( numActiveCells == (int)inputValues.size() );
#pragma omp parallel for #pragma omp parallel for
for ( int i = 0; i < numCells; i++ ) for ( int i = 0; i < numActiveCells; i++ )
{ {
if ( !visibility->val( i ) && activeCellInfo->isActive( i ) ) const auto reservoirCellIndex = activeReservoirCellIndices[i];
if ( !visibility->val( reservoirCellIndex ) )
{ {
size_t cellResultIndex = activeCellInfo->cellResultIndex( i ); resultValues[i] = inputValues[i];
resultValues[cellResultIndex] = inputValues[cellResultIndex];
} }
} }
} }
@@ -648,20 +678,21 @@ void RimGridCalculation::replaceFilteredValuesWithVector( const std::vector<doub
void RimGridCalculation::replaceFilteredValuesWithDefaultValue( double defaultValue, void RimGridCalculation::replaceFilteredValuesWithDefaultValue( double defaultValue,
cvf::ref<cvf::UByteArray> visibility, cvf::ref<cvf::UByteArray> visibility,
std::vector<double>& resultValues, std::vector<double>& resultValues,
RiaDefines::PorosityModelType porosityModel, RigActiveCellInfo* activeCellInfo )
RimEclipseCase* outputEclipseCase )
{ {
auto activeCellInfo = outputEclipseCase->eclipseCaseData()->activeCellInfo( porosityModel ); auto activeReservoirCellIndices = activeCellInfo->activeReservoirCellIndices();
int numCells = static_cast<int>( visibility->size() ); int numActiveCells = static_cast<int>( activeReservoirCellIndices.size() );
CAF_ASSERT( numActiveCells == (int)resultValues.size() );
#pragma omp parallel for #pragma omp parallel for
for ( int i = 0; i < numCells; i++ ) for ( int i = 0; i < numActiveCells; i++ )
{ {
if ( !visibility->val( i ) && activeCellInfo->isActive( i ) ) const auto reservoirCellIndex = activeReservoirCellIndices[i];
if ( !visibility->val( reservoirCellIndex ) )
{ {
size_t cellResultIndex = activeCellInfo->cellResultIndex( i ); resultValues[i] = defaultValue;
resultValues[cellResultIndex] = defaultValue;
} }
} }
} }
@@ -681,18 +712,20 @@ void RimGridCalculation::filterResults( RimGridView*
{ {
auto visibility = cellFilterView->currentTotalCellVisibility(); auto visibility = cellFilterView->currentTotalCellVisibility();
auto activeCellInfo = outputEclipseCase->eclipseCaseData()->activeCellInfo( porosityModel );
if ( defaultValueType == RimGridCalculation::DefaultValueType::FROM_PROPERTY ) if ( defaultValueType == RimGridCalculation::DefaultValueType::FROM_PROPERTY )
{ {
auto nonVisibleValues = getDataForResult( m_nonVisibleResultAddress->resultName(), auto nonVisibleValues = getActiveCellValues( m_nonVisibleResultAddress->resultName(),
m_nonVisibleResultAddress->resultType(), m_nonVisibleResultAddress->resultType(),
timeStep, timeStep,
porosityModel, porosityModel,
m_nonVisibleResultAddress->eclipseCase(), outputEclipseCase,
outputEclipseCase ); outputEclipseCase );
if ( !nonVisibleValues.empty() ) if ( !nonVisibleValues.empty() )
{ {
replaceFilteredValuesWithVector( nonVisibleValues, visibility, resultValues, porosityModel, outputEclipseCase ); replaceFilteredValuesWithVector( nonVisibleValues, visibility, resultValues, activeCellInfo );
} }
else else
{ {
@@ -706,7 +739,7 @@ void RimGridCalculation::filterResults( RimGridView*
double valueToUse = defaultValue; double valueToUse = defaultValue;
if ( defaultValueType == RimGridCalculation::DefaultValueType::POSITIVE_INFINITY ) valueToUse = HUGE_VAL; if ( defaultValueType == RimGridCalculation::DefaultValueType::POSITIVE_INFINITY ) valueToUse = HUGE_VAL;
replaceFilteredValuesWithDefaultValue( valueToUse, visibility, resultValues, porosityModel, outputEclipseCase ); replaceFilteredValuesWithDefaultValue( valueToUse, visibility, resultValues, activeCellInfo );
} }
} }
@@ -873,7 +906,7 @@ bool RimGridCalculation::calculateForCases( const std::vector<RimEclipseCase*>&
bool useDataFromSourceCase = ( v->eclipseCase() == m_destinationCase ); bool useDataFromSourceCase = ( v->eclipseCase() == m_destinationCase );
auto sourceCase = useDataFromSourceCase ? calculationCase : v->eclipseCase(); auto sourceCase = useDataFromSourceCase ? calculationCase : v->eclipseCase();
auto dataForVariable = getDataForVariable( v, tsId, porosityModel, sourceCase, calculationCase ); auto dataForVariable = getActiveCellValuesForVariable( v, tsId, porosityModel, sourceCase, calculationCase );
if ( dataForVariable.empty() ) if ( dataForVariable.empty() )
{ {
RiaLogging::error( QString( " No data found for variable '%1'." ).arg( v->name() ) ); RiaLogging::error( QString( " No data found for variable '%1'." ).arg( v->name() ) );
@@ -881,7 +914,8 @@ bool RimGridCalculation::calculateForCases( const std::vector<RimEclipseCase*>&
else if ( inputValueVisibilityFilter && hasAggregationExpression ) else if ( inputValueVisibilityFilter && hasAggregationExpression )
{ {
const double defaultValue = 0.0; const double defaultValue = 0.0;
replaceFilteredValuesWithDefaultValue( defaultValue, inputValueVisibilityFilter, dataForVariable, porosityModel, calculationCase ); auto activeCellInfo = calculationCase->eclipseCaseData()->activeCellInfo( porosityModel );
replaceFilteredValuesWithDefaultValue( defaultValue, inputValueVisibilityFilter, dataForVariable, activeCellInfo );
} }
dataForAllVariables.push_back( dataForVariable ); dataForAllVariables.push_back( dataForVariable );
@@ -896,10 +930,10 @@ bool RimGridCalculation::calculateForCases( const std::vector<RimEclipseCase*>&
} }
std::vector<double> resultValues; std::vector<double> resultValues;
if ( m_destinationCase && m_destinationCase->eclipseCaseData() ) if ( calculationCase && calculationCase->eclipseCaseData() )
{ {
// Find number of active cells in the destination case. // Find number of active cells in the destination case.
auto activeCellInfoDestination = m_destinationCase->eclipseCaseData()->activeCellInfo( porosityModel ); auto activeCellInfoDestination = calculationCase->eclipseCaseData()->activeCellInfo( porosityModel );
if ( activeCellInfoDestination ) if ( activeCellInfoDestination )
{ {
resultValues.resize( activeCellInfoDestination->reservoirActiveCellCount() ); resultValues.resize( activeCellInfoDestination->reservoirActiveCellCount() );

View File

@@ -34,6 +34,7 @@ class RimGridView;
class RigEclipseResultAddress; class RigEclipseResultAddress;
class RimEclipseResultAddress; class RimEclipseResultAddress;
class RimIdenticalGridCaseGroup; class RimIdenticalGridCaseGroup;
class RigActiveCellInfo;
//================================================================================================== //==================================================================================================
/// ///
@@ -88,13 +89,13 @@ protected:
std::pair<bool, QString> validateVariables(); std::pair<bool, QString> validateVariables();
std::vector<double> getDataForVariable( RimGridCalculationVariable* variable, std::vector<double> getActiveCellValuesForVariable( RimGridCalculationVariable* variable,
size_t tsId, size_t tsId,
RiaDefines::PorosityModelType porosityModel, RiaDefines::PorosityModelType porosityModel,
RimEclipseCase* sourceCase, RimEclipseCase* sourceCase,
RimEclipseCase* destinationCase ) const; RimEclipseCase* destinationCase ) const;
std::vector<double> getDataForResult( const QString& resultName, std::vector<double> getActiveCellValues( const QString& resultName,
const RiaDefines::ResultCatType resultCategoryType, const RiaDefines::ResultCatType resultCategoryType,
size_t tsId, size_t tsId,
RiaDefines::PorosityModelType porosityModel, RiaDefines::PorosityModelType porosityModel,
@@ -113,14 +114,12 @@ protected:
static void replaceFilteredValuesWithVector( const std::vector<double>& inputValues, static void replaceFilteredValuesWithVector( const std::vector<double>& inputValues,
cvf::ref<cvf::UByteArray> visibility, cvf::ref<cvf::UByteArray> visibility,
std::vector<double>& resultValues, std::vector<double>& resultValues,
RiaDefines::PorosityModelType porosityModel, RigActiveCellInfo* activeCellInfo );
RimEclipseCase* outputEclipseCase );
static void replaceFilteredValuesWithDefaultValue( double defaultValue, static void replaceFilteredValuesWithDefaultValue( double defaultValue,
cvf::ref<cvf::UByteArray> visibility, cvf::ref<cvf::UByteArray> visibility,
std::vector<double>& resultValues, std::vector<double>& resultValues,
RiaDefines::PorosityModelType porosityModel, RigActiveCellInfo* activeCellInfo );
RimEclipseCase* outputEclipseCase );
using DefaultValueConfig = std::pair<RimGridCalculation::DefaultValueType, double>; using DefaultValueConfig = std::pair<RimGridCalculation::DefaultValueType, double>;
DefaultValueConfig defaultValueConfiguration() const; DefaultValueConfig defaultValueConfiguration() const;

View File

@@ -411,7 +411,7 @@ void RimSummaryCaseMainCollection::loadFileSummaryCaseData( std::vector<RimFileS
// If h5 mode, check all summary files and create or recreate h5 files if required // If h5 mode, check all summary files and create or recreate h5 files if required
#ifdef USE_HDF5 #ifdef USE_HDF5
{ {
if ( prefs->summaryDataReader() == RiaPreferencesSummary::SummaryReaderMode::HDF5_OPM_COMMON && prefs->createH5SummaryDataFiles() ) if ( prefs->summaryDataReader() == RiaPreferencesSummary::SummaryReaderMode::HDF5_OPM_COMMON )
{ {
int threadCount = 1; int threadCount = 1;
#ifdef USE_OPENMP #ifdef USE_OPENMP
@@ -433,7 +433,10 @@ void RimSummaryCaseMainCollection::loadFileSummaryCaseData( std::vector<RimFileS
h5FileNames.push_back( h5FilenameCandidate.toStdString() ); h5FileNames.push_back( h5FilenameCandidate.toStdString() );
} }
RifHdf5SummaryExporter::ensureHdf5FileIsCreatedMultithreaded( headerFileNames, h5FileNames, threadCount ); RifHdf5SummaryExporter::ensureHdf5FileIsCreatedMultithreaded( headerFileNames,
h5FileNames,
prefs->createH5SummaryDataFiles(),
threadCount );
} }
} }
#endif #endif

View File

@@ -1115,17 +1115,23 @@ void RigCaseCellResultsData::createPlaceholderResultEntries()
} }
// Cell Volume // Cell Volume
{
if ( !hasResultEntry( RigEclipseResultAddress( RiaDefines::ResultCatType::STATIC_NATIVE, RiaResultNames::riCellVolumeResultName() ) ) )
{ {
addStaticScalarResult( RiaDefines::ResultCatType::STATIC_NATIVE, RiaResultNames::riCellVolumeResultName(), needsToBeStored, 0 ); addStaticScalarResult( RiaDefines::ResultCatType::STATIC_NATIVE, RiaResultNames::riCellVolumeResultName(), needsToBeStored, 0 );
} }
}
// Mobile Pore Volume // Mobile Pore Volume
{ {
if ( hasResultEntry( RigEclipseResultAddress( RiaDefines::ResultCatType::STATIC_NATIVE, "PORV" ) ) ) if ( hasResultEntry( RigEclipseResultAddress( RiaDefines::ResultCatType::STATIC_NATIVE, "PORV" ) ) )
{
if ( !hasResultEntry( RigEclipseResultAddress( RiaDefines::ResultCatType::STATIC_NATIVE, RiaResultNames::mobilePoreVolumeName() ) ) )
{ {
addStaticScalarResult( RiaDefines::ResultCatType::STATIC_NATIVE, RiaResultNames::mobilePoreVolumeName(), needsToBeStored, 0 ); addStaticScalarResult( RiaDefines::ResultCatType::STATIC_NATIVE, RiaResultNames::mobilePoreVolumeName(), needsToBeStored, 0 );
} }
} }
}
// I/J/K indexes // I/J/K indexes
{ {
@@ -1581,6 +1587,13 @@ size_t RigCaseCellResultsData::findOrLoadKnownScalarResultByResultTypeOrder( con
//-------------------------------------------------------------------------------------------------- //--------------------------------------------------------------------------------------------------
size_t RigCaseCellResultsData::findOrLoadKnownScalarResultForTimeStep( const RigEclipseResultAddress& resVarAddr, size_t timeStepIndex ) size_t RigCaseCellResultsData::findOrLoadKnownScalarResultForTimeStep( const RigEclipseResultAddress& resVarAddr, size_t timeStepIndex )
{ {
size_t scalarResultIndex = findScalarResultIndexFromAddress( resVarAddr );
if ( scalarResultIndex == cvf::UNDEFINED_SIZE_T )
{
return cvf::UNDEFINED_SIZE_T;
}
if ( isDataPresent( scalarResultIndex ) ) return scalarResultIndex;
RiaDefines::ResultCatType type = resVarAddr.resultCatType(); RiaDefines::ResultCatType type = resVarAddr.resultCatType();
QString resultName = resVarAddr.resultName(); QString resultName = resVarAddr.resultName();
@@ -1609,7 +1622,6 @@ size_t RigCaseCellResultsData::findOrLoadKnownScalarResultForTimeStep( const Rig
return completionTypeScalarResultIndex; return completionTypeScalarResultIndex;
} }
size_t scalarResultIndex = findScalarResultIndexFromAddress( resVarAddr );
if ( scalarResultIndex == cvf::UNDEFINED_SIZE_T ) return cvf::UNDEFINED_SIZE_T; if ( scalarResultIndex == cvf::UNDEFINED_SIZE_T ) return cvf::UNDEFINED_SIZE_T;
if ( type == RiaDefines::ResultCatType::GENERATED ) if ( type == RiaDefines::ResultCatType::GENERATED )

View File

@@ -36,7 +36,11 @@ TEST( DISABLED_HDFTests, WriteToHdf5SummaryExporter )
std::string exportFileName = "e:/project/scratch_export/hdf_complete.h5"; std::string exportFileName = "e:/project/scratch_export/hdf_complete.h5";
int threadCount = 1; int threadCount = 1;
RifHdf5SummaryExporter::ensureHdf5FileIsCreatedMultithreaded( { file_path.toStdString() }, { exportFileName }, threadCount ); bool createEnhancedSummaryFiles = true;
RifHdf5SummaryExporter::ensureHdf5FileIsCreatedMultithreaded( { file_path.toStdString() },
{ exportFileName },
createEnhancedSummaryFiles,
threadCount );
} }
//-------------------------------------------------------------------------------------------------- //--------------------------------------------------------------------------------------------------

View File

@@ -1,17 +1,17 @@
set(RESINSIGHT_MAJOR_VERSION 2024) set(RESINSIGHT_MAJOR_VERSION 2024)
set(RESINSIGHT_MINOR_VERSION 03) set(RESINSIGHT_MINOR_VERSION 03)
set(RESINSIGHT_PATCH_VERSION 1) set(RESINSIGHT_PATCH_VERSION 2)
# Opional text with no restrictions # Opional text with no restrictions
set(RESINSIGHT_VERSION_TEXT "-dev") set(RESINSIGHT_VERSION_TEXT "-dev")
#set(RESINSIGHT_VERSION_TEXT "-RC_05") #set(RESINSIGHT_VERSION_TEXT "-RC_02")
# Optional text # Optional text
# Must be unique and increasing within one combination of major/minor/patch version # Must be unique and increasing within one combination of major/minor/patch version
# The uniqueness of this text is independent of RESINSIGHT_VERSION_TEXT # The uniqueness of this text is independent of RESINSIGHT_VERSION_TEXT
# Format of text must be ".xx" # Format of text must be ".xx"
set(RESINSIGHT_DEV_VERSION ".05") set(RESINSIGHT_DEV_VERSION ".01")
# https://github.com/CRAVA/crava/tree/master/libs/nrlib # https://github.com/CRAVA/crava/tree/master/libs/nrlib
set(NRLIB_GITHUB_SHA "ba35d4359882f1c6f5e9dc30eb95fe52af50fd6f") set(NRLIB_GITHUB_SHA "ba35d4359882f1c6f5e9dc30eb95fe52af50fd6f")