Skip to content
Merged
Show file tree
Hide file tree
Changes from all commits
Commits
File filter

Filter by extension

Filter by extension

Conversations
Failed to load comments.
Loading
Jump to
Jump to file
Failed to load files.
Loading
Diff view
Diff view
3 changes: 1 addition & 2 deletions ApplicationLibCode/ProjectDataModel/RimCornerPointCase.cpp
Original file line number Diff line number Diff line change
Expand Up @@ -380,8 +380,7 @@ void RimCornerPointCase::computeDepthRelatedResults( RimCornerPointCase& cornerP
{
if ( RiaPreferencesGrid::current()->autoComputeDepthRelatedProperties() )
{
cornerPointCase.results( RiaDefines::PorosityModelType::MATRIX_MODEL )->computeDepthRelatedResults();
cornerPointCase.results( RiaDefines::PorosityModelType::FRACTURE_MODEL )->computeDepthRelatedResults();
cornerPointCase.eclipseCaseData()->computeDepthRelatedResults();
}
}

Expand Down
3 changes: 1 addition & 2 deletions ApplicationLibCode/ProjectDataModel/RimEclipseInputCase.cpp
Original file line number Diff line number Diff line change
Expand Up @@ -226,8 +226,7 @@ bool RimEclipseInputCase::openEclipseGridFile()

if ( RiaPreferencesGrid::current()->autoComputeDepthRelatedProperties() )
{
results( RiaDefines::PorosityModelType::MATRIX_MODEL )->computeDepthRelatedResults();
results( RiaDefines::PorosityModelType::FRACTURE_MODEL )->computeDepthRelatedResults();
eclipseCaseData()->computeDepthRelatedResults();
}

results( RiaDefines::PorosityModelType::MATRIX_MODEL )->computeCellVolumes();
Expand Down
3 changes: 1 addition & 2 deletions ApplicationLibCode/ProjectDataModel/RimEclipseResultCase.cpp
Original file line number Diff line number Diff line change
Expand Up @@ -313,8 +313,7 @@ bool RimEclipseResultCase::importGridAndResultMetaData( bool showTimeStepFilter

if ( RiaPreferencesGrid::current()->autoComputeDepthRelatedProperties() )
{
results( RiaDefines::PorosityModelType::MATRIX_MODEL )->computeDepthRelatedResults();
results( RiaDefines::PorosityModelType::FRACTURE_MODEL )->computeDepthRelatedResults();
eclipseCaseData()->computeDepthRelatedResults();
}

results( RiaDefines::PorosityModelType::MATRIX_MODEL )->computeCellVolumes();
Expand Down
3 changes: 1 addition & 2 deletions ApplicationLibCode/ProjectDataModel/RimEmCase.cpp
Original file line number Diff line number Diff line change
Expand Up @@ -97,8 +97,7 @@ bool RimEmCase::openEclipseGridFile()

if ( RiaPreferencesGrid::current()->autoComputeDepthRelatedProperties() )
{
results( RiaDefines::PorosityModelType::MATRIX_MODEL )->computeDepthRelatedResults();
results( RiaDefines::PorosityModelType::FRACTURE_MODEL )->computeDepthRelatedResults();
eclipseCaseData()->computeDepthRelatedResults();
}

results( RiaDefines::PorosityModelType::MATRIX_MODEL )->computeCellVolumes();
Expand Down
3 changes: 1 addition & 2 deletions ApplicationLibCode/ProjectDataModel/RimRoffCase.cpp
Original file line number Diff line number Diff line change
Expand Up @@ -99,8 +99,7 @@ bool RimRoffCase::openEclipseGridFile()

if ( RiaPreferencesGrid::current()->autoComputeDepthRelatedProperties() )
{
results( RiaDefines::PorosityModelType::MATRIX_MODEL )->computeDepthRelatedResults();
results( RiaDefines::PorosityModelType::FRACTURE_MODEL )->computeDepthRelatedResults();
eclipseCaseData()->computeDepthRelatedResults();
}

results( RiaDefines::PorosityModelType::MATRIX_MODEL )->computeCellVolumes();
Expand Down
185 changes: 123 additions & 62 deletions ApplicationLibCode/ReservoirDataModel/RigCaseCellResultsData.cpp
Original file line number Diff line number Diff line change
Expand Up @@ -65,6 +65,7 @@
#include <QDateTime>

#include <algorithm>
#include <array>
#include <cmath>

//--------------------------------------------------------------------------------------------------
Expand Down Expand Up @@ -1898,10 +1899,16 @@ void RigCaseCellResultsData::testAndComputeSgasForTimeStep( size_t timeStepIndex
//--------------------------------------------------------------------------------------------------
///
//--------------------------------------------------------------------------------------------------
void RigCaseCellResultsData::computeDepthRelatedResults()
RigCaseCellResultsData::DepthResultBuffers RigCaseCellResultsData::prepareDepthRelatedResultArrays()
{
size_t actCellCount = activeCellInfo()->reservoirActiveCellCount();
if ( actCellCount == 0 ) return;
DepthResultBuffers buffers;
buffers.activeCellInfo = activeCellInfo();
buffers.actCellCount = activeCellInfo()->reservoirActiveCellCount();

// A porosity model with no active cells is left disabled.
if ( buffers.actCellCount == 0 ) return buffers;

const size_t actCellCount = buffers.actCellCount;

size_t depthResultIndex = findOrLoadKnownScalarResult( RigEclipseResultAddress( RiaDefines::ResultCatType::STATIC_NATIVE, "DEPTH" ) );
size_t dxResultIndex = findOrLoadKnownScalarResult( RigEclipseResultAddress( RiaDefines::ResultCatType::STATIC_NATIVE, "DX" ) );
Expand All @@ -1910,47 +1917,40 @@ void RigCaseCellResultsData::computeDepthRelatedResults()
size_t topsResultIndex = findOrLoadKnownScalarResult( RigEclipseResultAddress( RiaDefines::ResultCatType::STATIC_NATIVE, "TOPS" ) );
size_t bottomResultIndex = findOrLoadKnownScalarResult( RigEclipseResultAddress( RiaDefines::ResultCatType::STATIC_NATIVE, "BOTTOM" ) );

bool computeDepth = false;
bool computeDx = false;
bool computeDy = false;
bool computeDz = false;
bool computeTops = false;
bool computeBottom = false;

if ( depthResultIndex == cvf::UNDEFINED_SIZE_T )
{
depthResultIndex = addStaticScalarResult( RiaDefines::ResultCatType::STATIC_NATIVE, "DEPTH", false, actCellCount );
computeDepth = true;
depthResultIndex = addStaticScalarResult( RiaDefines::ResultCatType::STATIC_NATIVE, "DEPTH", false, actCellCount );
buffers.computeDepth = true;
}

if ( dxResultIndex == cvf::UNDEFINED_SIZE_T )
{
dxResultIndex = addStaticScalarResult( RiaDefines::ResultCatType::STATIC_NATIVE, "DX", false, actCellCount );
computeDx = true;
dxResultIndex = addStaticScalarResult( RiaDefines::ResultCatType::STATIC_NATIVE, "DX", false, actCellCount );
buffers.computeDx = true;
}

if ( dyResultIndex == cvf::UNDEFINED_SIZE_T )
{
dyResultIndex = addStaticScalarResult( RiaDefines::ResultCatType::STATIC_NATIVE, "DY", false, actCellCount );
computeDy = true;
dyResultIndex = addStaticScalarResult( RiaDefines::ResultCatType::STATIC_NATIVE, "DY", false, actCellCount );
buffers.computeDy = true;
}

if ( dzResultIndex == cvf::UNDEFINED_SIZE_T )
{
dzResultIndex = addStaticScalarResult( RiaDefines::ResultCatType::STATIC_NATIVE, "DZ", false, actCellCount );
computeDz = true;
dzResultIndex = addStaticScalarResult( RiaDefines::ResultCatType::STATIC_NATIVE, "DZ", false, actCellCount );
buffers.computeDz = true;
}

if ( topsResultIndex == cvf::UNDEFINED_SIZE_T )
{
topsResultIndex = addStaticScalarResult( RiaDefines::ResultCatType::STATIC_NATIVE, "TOPS", false, actCellCount );
computeTops = true;
topsResultIndex = addStaticScalarResult( RiaDefines::ResultCatType::STATIC_NATIVE, "TOPS", false, actCellCount );
buffers.computeTops = true;
}

if ( bottomResultIndex == cvf::UNDEFINED_SIZE_T )
{
bottomResultIndex = addStaticScalarResult( RiaDefines::ResultCatType::STATIC_NATIVE, "BOTTOM", false, actCellCount );
computeBottom = true;
bottomResultIndex = addStaticScalarResult( RiaDefines::ResultCatType::STATIC_NATIVE, "BOTTOM", false, actCellCount );
buffers.computeBottom = true;
}

std::vector<std::vector<double>>& depth = m_cellScalarResults[depthResultIndex];
Expand All @@ -1965,83 +1965,144 @@ void RigCaseCellResultsData::computeDepthRelatedResults()
if ( depth[0].size() < actCellCount )
{
depth[0].resize( actCellCount, std::numeric_limits<double>::max() );
computeDepth = true;
buffers.computeDepth = true;
}

if ( dx[0].size() < actCellCount )
{
dx[0].resize( actCellCount, std::numeric_limits<double>::max() );
computeDx = true;
buffers.computeDx = true;
}

if ( dy[0].size() < actCellCount )
{
dy[0].resize( actCellCount, std::numeric_limits<double>::max() );
computeDy = true;
buffers.computeDy = true;
}

if ( dz[0].size() < actCellCount )
{
dz[0].resize( actCellCount, std::numeric_limits<double>::max() );
computeDz = true;
buffers.computeDz = true;
}

if ( tops[0].size() < actCellCount )
{
tops[0].resize( actCellCount, std::numeric_limits<double>::max() );
computeTops = true;
buffers.computeTops = true;
}

if ( bottom[0].size() < actCellCount )
{
bottom[0].resize( actCellCount, std::numeric_limits<double>::max() );
computeBottom = true;
buffers.computeBottom = true;
}
}

#pragma omp parallel for
for ( long cellIdx = 0; cellIdx < static_cast<long>( m_ownerMainGrid->totalCellCount() ); cellIdx++ )
{
const RigCell& cell = m_ownerMainGrid->cell( cellIdx );
if ( cell.isInvalid() ) continue;
buffers.depth = &depth[0];
buffers.dx = &dx[0];
buffers.dy = &dy[0];
buffers.dz = &dz[0];
buffers.tops = &tops[0];
buffers.bottom = &bottom[0];

size_t resultIndex = activeCellInfo()->cellResultIndex( ReservoirCellIndex( cellIdx ) ).value();
if ( resultIndex == cvf::UNDEFINED_SIZE_T ) continue;
if ( resultIndex >= actCellCount ) continue;
return buffers;
}

bool isTemporaryGrid = cell.hostGrid()->isTempGrid();
//--------------------------------------------------------------------------------------------------
///
//--------------------------------------------------------------------------------------------------
void RigCaseCellResultsData::computeDepthRelatedResults( RigCaseCellResultsData* matrixResults, RigCaseCellResultsData* fractureResults )
{
RigMainGrid* mainGrid = nullptr;
if ( matrixResults ) mainGrid = matrixResults->m_ownerMainGrid;
if ( !mainGrid && fractureResults ) mainGrid = fractureResults->m_ownerMainGrid;
if ( !mainGrid ) return;

if ( computeDepth || isTemporaryGrid )
{
depth[0][resultIndex] = -cell.center().z();
}
// Collect the enabled (non-empty) porosity models. Both share the same main grid, so the
// geometry of each cell only needs to be computed once and is written to every model in which
// the cell is active.
std::vector<DepthResultBuffers> buffers;
for ( RigCaseCellResultsData* results : { matrixResults, fractureResults } )
{
if ( !results ) continue;
DepthResultBuffers b = results->prepareDepthRelatedResultArrays();
if ( b.actCellCount == 0 ) continue;
buffers.push_back( b );
}

if ( computeDx || isTemporaryGrid )
{
cvf::Vec3d cellWidth = cell.faceCenter( cvf::StructGridInterface::NEG_I ) - cell.faceCenter( cvf::StructGridInterface::POS_I );
dx[0][resultIndex] = cellWidth.length();
}
if ( buffers.empty() ) return;

if ( computeDy || isTemporaryGrid )
{
cvf::Vec3d cellWidth = cell.faceCenter( cvf::StructGridInterface::NEG_J ) - cell.faceCenter( cvf::StructGridInterface::POS_J );
dy[0][resultIndex] = cellWidth.length();
}
#pragma omp parallel for
for ( long cellIdx = 0; cellIdx < static_cast<long>( mainGrid->totalCellCount() ); cellIdx++ )
{
const RigCell& cell = mainGrid->cell( cellIdx );
if ( cell.isInvalid() ) continue;

if ( computeDz || isTemporaryGrid )
{
cvf::Vec3d cellWidth = cell.faceCenter( cvf::StructGridInterface::NEG_K ) - cell.faceCenter( cvf::StructGridInterface::POS_K );
dz[0][resultIndex] = cellWidth.length();
}
const bool isTemporaryGrid = cell.hostGrid()->isTempGrid();

// Resolve this cell's result index in each enabled model, and gather which properties any
// active model still needs (temporary grids are always recomputed). Skip the cell entirely
// if it is inactive in every model. At most two porosity models (matrix and fracture) are
// present.
std::array<size_t, 2> resultIndices;
bool anyActive = false;
bool needDepth = isTemporaryGrid;
bool needDx = isTemporaryGrid;
bool needDy = isTemporaryGrid;
bool needDz = isTemporaryGrid;
bool needTops = isTemporaryGrid;
bool needBottom = isTemporaryGrid;
for ( size_t i = 0; i < buffers.size(); i++ )
{
size_t resultIndex = buffers[i].activeCellInfo->cellResultIndex( ReservoirCellIndex( cellIdx ) ).value();
if ( resultIndex == cvf::UNDEFINED_SIZE_T || resultIndex >= buffers[i].actCellCount )
{
resultIndices[i] = cvf::UNDEFINED_SIZE_T;
continue;
}

if ( computeTops || isTemporaryGrid )
{
tops[0][resultIndex] = -cell.faceCenter( cvf::StructGridInterface::NEG_K ).z();
}
resultIndices[i] = resultIndex;
anyActive = true;
needDepth = needDepth || buffers[i].computeDepth;
needDx = needDx || buffers[i].computeDx;
needDy = needDy || buffers[i].computeDy;
needDz = needDz || buffers[i].computeDz;
needTops = needTops || buffers[i].computeTops;
needBottom = needBottom || buffers[i].computeBottom;
}
if ( !anyActive ) continue;

// The geometry is shared between the porosity models, so each value is computed at most once
// (only if some active model needs it) and then written to every active model that needs it.
double depthValue = needDepth ? -cell.center().z() : 0.0;
double dxValue =
needDx ? ( cell.faceCenter( cvf::StructGridInterface::NEG_I ) - cell.faceCenter( cvf::StructGridInterface::POS_I ) ).length() : 0.0;
double dyValue =
needDy ? ( cell.faceCenter( cvf::StructGridInterface::NEG_J ) - cell.faceCenter( cvf::StructGridInterface::POS_J ) ).length() : 0.0;
double dzValue =
needDz ? ( cell.faceCenter( cvf::StructGridInterface::NEG_K ) - cell.faceCenter( cvf::StructGridInterface::POS_K ) ).length() : 0.0;
double topsValue = needTops ? -cell.faceCenter( cvf::StructGridInterface::NEG_K ).z() : 0.0;
double bottomValue = needBottom ? -cell.faceCenter( cvf::StructGridInterface::POS_K ).z() : 0.0;

// Write a value into one model's result row, honoring its per-property compute flag.
auto assign = [&]( std::vector<double>* row, bool compute, size_t resultIndex, double value )
{
if ( resultIndex != cvf::UNDEFINED_SIZE_T && ( compute || isTemporaryGrid ) )
{
( *row )[resultIndex] = value;
}
};

if ( computeBottom || isTemporaryGrid )
for ( size_t i = 0; i < buffers.size(); i++ )
{
bottom[0][resultIndex] = -cell.faceCenter( cvf::StructGridInterface::POS_K ).z();
const DepthResultBuffers& b = buffers[i];
assign( b.depth, b.computeDepth, resultIndices[i], depthValue );
assign( b.dx, b.computeDx, resultIndices[i], dxValue );
assign( b.dy, b.computeDy, resultIndices[i], dyValue );
assign( b.dz, b.computeDz, resultIndices[i], dzValue );
assign( b.tops, b.computeTops, resultIndices[i], topsValue );
assign( b.bottom, b.computeBottom, resultIndices[i], bottomValue );
}
}
}
Expand Down
29 changes: 28 additions & 1 deletion ApplicationLibCode/ReservoirDataModel/RigCaseCellResultsData.h
Original file line number Diff line number Diff line change
Expand Up @@ -142,7 +142,12 @@ class RigCaseCellResultsData : public cvf::Object
void createResultEntry( const RigEclipseResultAddress& resultAddress, bool needsToBeStored );
bool updateResultDataType( const RigEclipseResultAddress& resultAddress, RiaDefines::ResultDataType dataType );
void createPlaceholderResultEntries();
void computeDepthRelatedResults();

// Compute depth-related geometry results (DEPTH/DX/DY/DZ/TOPS/BOTTOM) for both porosity models
// in a single traversal of the shared grid. The values are derived purely from the grid
// geometry, so a cell active in both models is computed only once and written to both.
static void computeDepthRelatedResults( RigCaseCellResultsData* matrixResults, RigCaseCellResultsData* fractureResults );

void computeCellVolumes();
bool hasFlowDiagUsableFluxes() const;

Expand All @@ -160,6 +165,28 @@ class RigCaseCellResultsData : public cvf::Object
void clearAllResultAliases();

private:
// Per-model buffers used by computeDepthRelatedResults(). Holds pointers to the result rows
// and per-property flags telling whether the row still needs to be computed. A buffer with
// actCellCount == 0 is disabled (the porosity model has no active cells).
struct DepthResultBuffers
{
RigActiveCellInfo* activeCellInfo = nullptr;
size_t actCellCount = 0;
std::vector<double>* depth = nullptr;
std::vector<double>* dx = nullptr;
std::vector<double>* dy = nullptr;
std::vector<double>* dz = nullptr;
std::vector<double>* tops = nullptr;
std::vector<double>* bottom = nullptr;
bool computeDepth = false;
bool computeDx = false;
bool computeDy = false;
bool computeDz = false;
bool computeTops = false;
bool computeBottom = false;
};
DepthResultBuffers prepareDepthRelatedResultArrays();

size_t findOrLoadKnownScalarResult( const RigEclipseResultAddress& resVarAddr );
size_t findOrLoadKnownScalarResultByResultTypeOrder( const RigEclipseResultAddress& resVarAddr,
const std::vector<RiaDefines::ResultCatType>& resultCategorySearchOrder );
Expand Down
8 changes: 8 additions & 0 deletions ApplicationLibCode/ReservoirDataModel/RigEclipseCaseData.cpp
Original file line number Diff line number Diff line change
Expand Up @@ -467,6 +467,14 @@ void RigEclipseCaseData::computeActiveCellBoundingBoxes( bool useOptimizedVersio
computeActiveCellsGeometryBoundingBoxSlow();
}

//--------------------------------------------------------------------------------------------------
///
//--------------------------------------------------------------------------------------------------
void RigEclipseCaseData::computeDepthRelatedResults()
{
RigCaseCellResultsData::computeDepthRelatedResults( m_matrixModelResults.p(), m_fractureModelResults.p() );
}

//--------------------------------------------------------------------------------------------------
///
//--------------------------------------------------------------------------------------------------
Expand Down
2 changes: 2 additions & 0 deletions ApplicationLibCode/ReservoirDataModel/RigEclipseCaseData.h
Original file line number Diff line number Diff line change
Expand Up @@ -104,6 +104,8 @@ class RigEclipseCaseData : public cvf::Object

void computeActiveCellBoundingBoxes( bool useOptimizedVersion );

void computeDepthRelatedResults();

RiaDefines::EclipseUnitSystem unitsType() const { return m_unitsType; }
void setUnitsType( RiaDefines::EclipseUnitSystem unitsType ) { m_unitsType = unitsType; }

Expand Down
Loading