Ensemble surface import and statistics

This commit is contained in:
Kristian Bendiksen
2021-08-17 13:38:12 +02:00
committed by GitHub
parent d1e81f3c1e
commit 966bcd1e77
37 changed files with 2138 additions and 34 deletions

View File

@@ -7,6 +7,9 @@ ${CMAKE_CURRENT_LIST_DIR}/RimSurfaceCollection.h
${CMAKE_CURRENT_LIST_DIR}/RimSurfaceInView.h
${CMAKE_CURRENT_LIST_DIR}/RimSurfaceInViewCollection.h
${CMAKE_CURRENT_LIST_DIR}/RimSurfaceResultDefinition.h
${CMAKE_CURRENT_LIST_DIR}/RimEnsembleSurface.h
${CMAKE_CURRENT_LIST_DIR}/RimEnsembleSurfaceInView.h
${CMAKE_CURRENT_LIST_DIR}/RimEnsembleStatisticsSurface.h
)
set (SOURCE_GROUP_SOURCE_FILES
@@ -17,6 +20,9 @@ ${CMAKE_CURRENT_LIST_DIR}/RimSurfaceCollection.cpp
${CMAKE_CURRENT_LIST_DIR}/RimSurfaceInView.cpp
${CMAKE_CURRENT_LIST_DIR}/RimSurfaceInViewCollection.cpp
${CMAKE_CURRENT_LIST_DIR}/RimSurfaceResultDefinition.cpp
${CMAKE_CURRENT_LIST_DIR}/RimEnsembleSurface.cpp
${CMAKE_CURRENT_LIST_DIR}/RimEnsembleSurfaceInView.cpp
${CMAKE_CURRENT_LIST_DIR}/RimEnsembleStatisticsSurface.cpp
)
list(APPEND CODE_HEADER_FILES

View File

@@ -0,0 +1,139 @@
/////////////////////////////////////////////////////////////////////////////////
//
// Copyright (C) 2020- Equinor ASA
//
// ResInsight is free software: you can redistribute it and/or modify
// it under the terms of the GNU General Public License as published by
// the Free Software Foundation, either version 3 of the License, or
// (at your option) any later version.
//
// ResInsight is distributed in the hope that it will be useful, but WITHOUT ANY
// WARRANTY; without even the implied warranty of MERCHANTABILITY or
// FITNESS FOR A PARTICULAR PURPOSE.
//
// See the GNU General Public License at <http://www.gnu.org/licenses/gpl.html>
// for more details.
//
/////////////////////////////////////////////////////////////////////////////////
#include "RimEnsembleStatisticsSurface.h"
#include "RigSurface.h"
#include "RigSurfaceStatisticsCalculator.h"
#include "RimEnsembleSurface.h"
#include "RimSurfaceCollection.h"
#include "cafPdmFieldScriptingCapability.h"
#include "cafPdmObjectScriptingCapability.h"
#include <QFileInfo>
// TODO: Use the alias concept prototyped below when the alias concept for class is ready
// CAF_PDM_SOURCE_INIT( RimEnsembleStatisticsSurface, "EnsembleStatisticsSurface", "Surface" );
// CAF_PDM_SOURCE_INIT( <class> , <keyword> , <alias>);
CAF_PDM_SOURCE_INIT( RimEnsembleStatisticsSurface, "EnsembleStatisticsSurface" );
//--------------------------------------------------------------------------------------------------
///
//--------------------------------------------------------------------------------------------------
RimEnsembleStatisticsSurface::RimEnsembleStatisticsSurface()
{
CAF_PDM_InitScriptableObject( "Surface", ":/ReservoirSurface16x16.png", "", "" );
CAF_PDM_InitFieldNoDefault( &m_statisticsType, "StatisticsType", "StatisticsType", "", "", "" );
}
//--------------------------------------------------------------------------------------------------
///
//--------------------------------------------------------------------------------------------------
RimEnsembleStatisticsSurface::~RimEnsembleStatisticsSurface()
{
}
//--------------------------------------------------------------------------------------------------
///
//--------------------------------------------------------------------------------------------------
void RimEnsembleStatisticsSurface::setStatisticsType( RigSurfaceStatisticsCalculator::StatisticsType statisticsType )
{
m_statisticsType = statisticsType;
}
//--------------------------------------------------------------------------------------------------
///
//--------------------------------------------------------------------------------------------------
QString RimEnsembleStatisticsSurface::fullName() const
{
return caf::AppEnum<RigSurfaceStatisticsCalculator::StatisticsType>::uiText( m_statisticsType.v() );
}
//--------------------------------------------------------------------------------------------------
///
//--------------------------------------------------------------------------------------------------
bool RimEnsembleStatisticsSurface::onLoadData()
{
return updateSurfaceData();
}
//--------------------------------------------------------------------------------------------------
///
//--------------------------------------------------------------------------------------------------
RimSurface* RimEnsembleStatisticsSurface::createCopy()
{
RimEnsembleStatisticsSurface* newSurface = dynamic_cast<RimEnsembleStatisticsSurface*>(
xmlCapability()->copyByXmlSerialization( caf::PdmDefaultObjectFactory::instance() ) );
if ( !newSurface->onLoadData() )
{
delete newSurface;
return nullptr;
}
return newSurface;
}
//--------------------------------------------------------------------------------------------------
///
//--------------------------------------------------------------------------------------------------
bool RimEnsembleStatisticsSurface ::updateSurfaceData()
{
RimEnsembleSurface* ensembleSurface;
firstAncestorOrThisOfType( ensembleSurface );
if ( ensembleSurface )
{
const RigSurface* surface = ensembleSurface->statisticsSurface();
if ( surface )
{
const std::vector<unsigned int>& indices = surface->triangleIndices();
const std::vector<cvf::Vec3d>& vertices = surface->vertices();
const std::vector<float>& meanValues = surface->propertyValues(
caf::AppEnum<RigSurfaceStatisticsCalculator::StatisticsType>::text( m_statisticsType.v() ) );
std::vector<cvf::Vec3d> verts;
for ( size_t i = 0; i < vertices.size(); i++ )
{
verts.push_back( cvf::Vec3d( vertices[i].x(), vertices[i].y(), meanValues[i] ) );
}
m_tringleIndices = indices;
m_vertices = verts;
m_surfaceData = new RigSurface;
m_surfaceData->setTriangleData( m_tringleIndices, m_vertices );
return true;
}
}
return false;
}
//--------------------------------------------------------------------------------------------------
///
//--------------------------------------------------------------------------------------------------
void RimEnsembleStatisticsSurface ::clearCachedNativeData()
{
}

View File

@@ -0,0 +1,52 @@
/////////////////////////////////////////////////////////////////////////////////
//
// Copyright (C) 2021- Equinor ASA
//
// ResInsight is free software: you can redistribute it and/or modify
// it under the terms of the GNU General Public License as published by
// the Free Software Foundation, either version 3 of the License, or
// (at your option) any later version.
//
// ResInsight is distributed in the hope that it will be useful, but WITHOUT ANY
// WARRANTY; without even the implied warranty of MERCHANTABILITY or
// FITNESS FOR A PARTICULAR PURPOSE.
//
// See the GNU General Public License at <http://www.gnu.org/licenses/gpl.html>
// for more details.
//
/////////////////////////////////////////////////////////////////////////////////
#pragma once
#include "RigSurface.h"
#include "RigSurfaceStatisticsCalculator.h"
#include "RimSurface.h"
#include "cafAppEnum.h"
class RimEnsembleStatisticsSurface : public RimSurface
{
CAF_PDM_HEADER_INIT;
public:
RimEnsembleStatisticsSurface();
~RimEnsembleStatisticsSurface() override;
bool onLoadData() override;
RimSurface* createCopy() override;
void setStatisticsType( RigSurfaceStatisticsCalculator::StatisticsType statisticsType );
QString fullName() const override;
protected:
bool updateSurfaceData() override;
void clearCachedNativeData() override;
private:
std::vector<unsigned> m_tringleIndices;
std::vector<cvf::Vec3d> m_vertices;
caf::PdmField<caf::AppEnum<RigSurfaceStatisticsCalculator::StatisticsType>> m_statisticsType;
};

View File

@@ -0,0 +1,279 @@
/////////////////////////////////////////////////////////////////////////////////
//
// Copyright (C) 2021- Equinor ASA
//
// ResInsight is free software: you can redistribute it and/or modify
// it under the terms of the GNU General Public License as published by
// the Free Software Foundation, either version 3 of the License, or
// (at your option) any later version.
//
// ResInsight is distributed in the hope that it will be useful, but WITHOUT ANY
// WARRANTY; without even the implied warranty of MERCHANTABILITY or
// FITNESS FOR A PARTICULAR PURPOSE.
//
// See the GNU General Public License at <http://www.gnu.org/licenses/gpl.html>
// for more details.
//
/////////////////////////////////////////////////////////////////////////////////
#include "RimEnsembleSurface.h"
#include "RiaLogging.h"
#include "RigSurfaceResampler.h"
#include "RigSurfaceStatisticsCalculator.h"
#include "RimEnsembleCurveSet.h"
#include "RimEnsembleStatisticsSurface.h"
#include "RimFileSurface.h"
#include "RimMainPlotCollection.h"
#include "RimProject.h"
#include "RimSurfaceCollection.h"
#include "cafPdmFieldScriptingCapability.h"
#include "cafPdmObjectScriptingCapability.h"
CAF_PDM_SOURCE_INIT( RimEnsembleSurface, "EnsembleSurface" );
//--------------------------------------------------------------------------------------------------
///
//--------------------------------------------------------------------------------------------------
RimEnsembleSurface::RimEnsembleSurface()
{
CAF_PDM_InitScriptableObject( "Ensemble Surface", ":/ReservoirSurfaces16x16.png", "", "" );
CAF_PDM_InitFieldNoDefault( &m_fileSurfaces, "FileSurfaces", "", "", "", "" );
m_fileSurfaces.uiCapability()->setUiHidden( true );
CAF_PDM_InitFieldNoDefault( &m_statisticsSurfaces, "StatisticsSurfaces", "", "", "", "" );
m_statisticsSurfaces.uiCapability()->setUiHidden( true );
CAF_PDM_InitFieldNoDefault( &m_ensembleCurveSet, "FilterEnsembleCurveSet", "Filter by Ensemble Curve Set", "", "", "" );
}
//--------------------------------------------------------------------------------------------------
///
//--------------------------------------------------------------------------------------------------
void RimEnsembleSurface::removeFileSurface( RimFileSurface* fileSurface )
{
m_fileSurfaces.removeChildObject( fileSurface );
}
//--------------------------------------------------------------------------------------------------
///
//--------------------------------------------------------------------------------------------------
void RimEnsembleSurface::addFileSurface( RimFileSurface* fileSurface )
{
m_fileSurfaces.push_back( fileSurface );
}
//--------------------------------------------------------------------------------------------------
///
//--------------------------------------------------------------------------------------------------
std::vector<RimFileSurface*> RimEnsembleSurface::fileSurfaces() const
{
return m_fileSurfaces().childObjects();
}
//--------------------------------------------------------------------------------------------------
///
//--------------------------------------------------------------------------------------------------
std::vector<RimSurface*> RimEnsembleSurface::surfaces() const
{
std::vector<RimSurface*> surfaces;
for ( auto fs : m_fileSurfaces.childObjects() )
surfaces.push_back( fs );
for ( auto s : m_statisticsSurfaces.childObjects() )
surfaces.push_back( s );
return surfaces;
}
//--------------------------------------------------------------------------------------------------
///
//--------------------------------------------------------------------------------------------------
void RimEnsembleSurface::loadDataAndUpdate()
{
for ( auto& w : m_fileSurfaces )
{
if ( !w->onLoadData() )
{
RiaLogging::warning( QString( "Failed to load surface: %1" ).arg( w->surfaceFilePath() ) );
}
}
std::vector<RimFileSurface*> fileSurfaces = m_fileSurfaces.childObjects();
if ( m_ensembleCurveSet != nullptr )
{
fileSurfaces = filterByEnsembleCurveSet( fileSurfaces );
}
m_statisticsSurfaces.deleteAllChildObjects();
m_statisticsSurfaces.clear();
if ( !fileSurfaces.empty() )
{
cvf::ref<RigSurface> firstSurface = fileSurfaces[0]->surfaceData();
std::vector<cvf::ref<RigSurface>> surfaces;
for ( auto& w : fileSurfaces )
surfaces.push_back( RigSurfaceResampler::resampleSurface( firstSurface, w->surfaceData() ) );
m_statisticsSurface = RigSurfaceStatisticsCalculator::computeStatistics( surfaces );
if ( !m_statisticsSurface.isNull() )
{
std::vector<RigSurfaceStatisticsCalculator::StatisticsType> statisticsTypes =
{ RigSurfaceStatisticsCalculator::StatisticsType::MIN,
RigSurfaceStatisticsCalculator::StatisticsType::MAX,
RigSurfaceStatisticsCalculator::StatisticsType::MEAN,
RigSurfaceStatisticsCalculator::StatisticsType::P10,
RigSurfaceStatisticsCalculator::StatisticsType::P50,
RigSurfaceStatisticsCalculator::StatisticsType::P90 };
for ( auto s : statisticsTypes )
{
auto statSurface = new RimEnsembleStatisticsSurface;
statSurface->setStatisticsType( s );
m_statisticsSurfaces.push_back( statSurface );
statSurface->onLoadData();
}
}
}
RimSurfaceCollection* surfColl;
this->firstAncestorOrThisOfTypeAsserted( surfColl );
std::vector<RimSurface*> surfacesToUpdate;
surfColl->updateViews( surfaces(), false );
updateConnectedEditors();
}
//--------------------------------------------------------------------------------------------------
///
//--------------------------------------------------------------------------------------------------
std::vector<RimFileSurface*>
RimEnsembleSurface::filterByEnsembleCurveSet( const std::vector<RimFileSurface*>& fileSurfaces ) const
{
std::vector<RimFileSurface*> filteredCases;
if ( m_ensembleCurveSet != nullptr )
{
// Get the summary cases from the related ensemble summary curve set.
RimSummaryCaseCollection* summaryCaseCollection = m_ensembleCurveSet->summaryCaseCollection();
//
std::vector<RimSummaryCase*> sumCases =
m_ensembleCurveSet->filterEnsembleCases( summaryCaseCollection->allSummaryCases() );
for ( auto sumCase : sumCases )
{
for ( auto fileSurface : fileSurfaces )
{
if ( isSameRealization( sumCase, fileSurface ) )
{
filteredCases.push_back( fileSurface );
}
}
}
}
else
{
filteredCases = fileSurfaces;
}
return filteredCases;
}
//--------------------------------------------------------------------------------------------------
///
//--------------------------------------------------------------------------------------------------
bool RimEnsembleSurface::isSameRealization( RimSummaryCase* summaryCase, RimFileSurface* fileSurface ) const
{
// TODO: duplication with RimEnsembleWellLogCurveSet::isSameRealization
QString fileSurfaceName = fileSurface->surfaceFilePath();
if ( summaryCase->hasCaseRealizationParameters() )
{
// TODO: make less naive..
int realizationNumber = summaryCase->caseRealizationParameters()->realizationNumber();
QString summaryCaseFileName = summaryCase->summaryHeaderFilename();
if ( fileSurfaceName.contains( QString( "realization-%1" ).arg( realizationNumber ) ) )
{
return true;
}
}
return false;
}
//--------------------------------------------------------------------------------------------------
///
//--------------------------------------------------------------------------------------------------
const RigSurface* RimEnsembleSurface::statisticsSurface() const
{
return m_statisticsSurface.p();
}
//--------------------------------------------------------------------------------------------------
///
//--------------------------------------------------------------------------------------------------
QList<caf::PdmOptionItemInfo> RimEnsembleSurface::calculateValueOptions( const caf::PdmFieldHandle* fieldNeedingOptions,
bool* useOptionsOnly )
{
QList<caf::PdmOptionItemInfo> options;
if ( fieldNeedingOptions == &m_ensembleCurveSet )
{
options.push_back( caf::PdmOptionItemInfo( "None", nullptr ) );
RimMainPlotCollection* mainPlotColl = RimProject::current()->mainPlotCollection();
std::vector<RimEnsembleCurveSet*> ensembleCurveSets;
mainPlotColl->descendantsOfType( ensembleCurveSets );
for ( auto ensembleCurveSet : ensembleCurveSets )
{
options.push_back( caf::PdmOptionItemInfo( ensembleCurveSet->name(), ensembleCurveSet ) );
}
}
return options;
}
//--------------------------------------------------------------------------------------------------
///
//--------------------------------------------------------------------------------------------------
void RimEnsembleSurface::connectEnsembleCurveSetFilterSignals()
{
if ( m_ensembleCurveSet() )
{
m_ensembleCurveSet()->filterChanged.connect( this, &RimEnsembleSurface::onFilterSourceChanged );
}
}
//--------------------------------------------------------------------------------------------------
///
//--------------------------------------------------------------------------------------------------
void RimEnsembleSurface::onFilterSourceChanged( const caf::SignalEmitter* emitter )
{
if ( m_ensembleCurveSet() ) loadDataAndUpdate();
}
//--------------------------------------------------------------------------------------------------
///
//--------------------------------------------------------------------------------------------------
void RimEnsembleSurface::initAfterRead()
{
connectEnsembleCurveSetFilterSignals();
}
//--------------------------------------------------------------------------------------------------
///
//--------------------------------------------------------------------------------------------------
void RimEnsembleSurface::fieldChangedByUi( const caf::PdmFieldHandle* changedField,
const QVariant& oldValue,
const QVariant& newValue )
{
if ( changedField == &m_ensembleCurveSet )
{
connectEnsembleCurveSetFilterSignals();
loadDataAndUpdate();
}
}

View File

@@ -0,0 +1,75 @@
/////////////////////////////////////////////////////////////////////////////////
//
// Copyright (C) 2021- Equinor ASA
//
// ResInsight is free software: you can redistribute it and/or modify
// it under the terms of the GNU General Public License as published by
// the Free Software Foundation, either version 3 of the License, or
// (at your option) any later version.
//
// ResInsight is distributed in the hope that it will be useful, but WITHOUT ANY
// WARRANTY; without even the implied warranty of MERCHANTABILITY or
// FITNESS FOR A PARTICULAR PURPOSE.
//
// See the GNU General Public License at <http://www.gnu.org/licenses/gpl.html>
// for more details.
//
/////////////////////////////////////////////////////////////////////////////////
#pragma once
#include "RimNamedObject.h"
#include "cafPdmChildArrayField.h"
#include "cafPdmPtrField.h"
#include "cvfObject.h"
class RimFileSurface;
class RimSurface;
class RigSurface;
class RimEnsembleStatisticsSurface;
class RimEnsembleCurveSet;
class RimSummaryCase;
//==================================================================================================
///
//==================================================================================================
class RimEnsembleSurface : public RimNamedObject
{
CAF_PDM_HEADER_INIT;
public:
RimEnsembleSurface();
void removeFileSurface( RimFileSurface* fileSurface );
void addFileSurface( RimFileSurface* fileSurface );
std::vector<RimFileSurface*> fileSurfaces() const;
std::vector<RimSurface*> surfaces() const;
void loadDataAndUpdate();
const RigSurface* statisticsSurface() const;
protected:
QList<caf::PdmOptionItemInfo> calculateValueOptions( const caf::PdmFieldHandle* fieldNeedingOptions,
bool* useOptionsOnly ) override;
void fieldChangedByUi( const caf::PdmFieldHandle* changedField, const QVariant& oldValue, const QVariant& newValue ) override;
void initAfterRead() override;
std::vector<RimFileSurface*> filterByEnsembleCurveSet( const std::vector<RimFileSurface*>& fileSurfaces ) const;
bool isSameRealization( RimSummaryCase* summaryCase, RimFileSurface* fileSurface ) const;
private:
void connectEnsembleCurveSetFilterSignals();
void onFilterSourceChanged( const caf::SignalEmitter* emitter );
caf::PdmChildArrayField<RimFileSurface*> m_fileSurfaces;
caf::PdmChildArrayField<RimEnsembleStatisticsSurface*> m_statisticsSurfaces;
caf::PdmPtrField<RimEnsembleCurveSet*> m_ensembleCurveSet;
cvf::ref<RigSurface> m_statisticsSurface;
};

View File

@@ -0,0 +1,342 @@
/////////////////////////////////////////////////////////////////////////////////
//
// Copyright (C) 2021- Equinor ASA
//
// ResInsight is free software: you can redistribute it and/or modify
// it under the terms of the GNU General Public License as published by
// the Free Software Foundation, either version 3 of the License, or
// (at your option) any later version.
//
// ResInsight is distributed in the hope that it will be useful, but WITHOUT ANY
// WARRANTY; without even the implied warranty of MERCHANTABILITY or
// FITNESS FOR A PARTICULAR PURPOSE.
//
// See the GNU General Public License at <http://www.gnu.org/licenses/gpl.html>
// for more details.
//
/////////////////////////////////////////////////////////////////////////////////
#include "RimEnsembleSurfaceInView.h"
#include "RimEnsembleSurface.h"
#include "RimGridView.h"
#include "RimIntersectionResultDefinition.h"
#include "RimSurface.h"
#include "RimSurfaceCollection.h"
#include "RimSurfaceInView.h"
#include "RimSurfaceResultDefinition.h"
#include "RivSurfacePartMgr.h"
#include "cvfModelBasicList.h"
CAF_PDM_SOURCE_INIT( RimEnsembleSurfaceInView, "EnsembleSurfaceInView" );
//--------------------------------------------------------------------------------------------------
///
//--------------------------------------------------------------------------------------------------
RimEnsembleSurfaceInView::RimEnsembleSurfaceInView()
{
CAF_PDM_InitObject( "Ensemble Surface", ":/ReservoirSurfaces16x16.png", "", "" );
CAF_PDM_InitFieldNoDefault( &m_ensembleSurfaceName, "EnsembleSurfaceName", "EnsembleSurfaceName", "", "", "" );
m_ensembleSurfaceName.registerGetMethod( this, &RimEnsembleSurfaceInView::name );
m_ensembleSurfaceName.uiCapability()->setUiReadOnly( true );
m_ensembleSurfaceName.xmlCapability()->disableIO();
CAF_PDM_InitFieldNoDefault( &m_surfacesInView, "SurfacesInViewField", "SurfacesInViewField", "", "", "" );
m_surfacesInView.uiCapability()->setUiTreeHidden( true );
CAF_PDM_InitFieldNoDefault( &m_ensembleSurface, "EnsembleSurface", "EnsembleSurface", "", "", "" );
m_ensembleSurface.uiCapability()->setUiTreeHidden( true );
nameField()->uiCapability()->setUiHidden( true );
}
//--------------------------------------------------------------------------------------------------
///
//--------------------------------------------------------------------------------------------------
RimEnsembleSurfaceInView::~RimEnsembleSurfaceInView()
{
}
//--------------------------------------------------------------------------------------------------
///
//--------------------------------------------------------------------------------------------------
caf::PdmFieldHandle* RimEnsembleSurfaceInView::userDescriptionField()
{
return &m_ensembleSurfaceName;
}
//--------------------------------------------------------------------------------------------------
///
//--------------------------------------------------------------------------------------------------
QString RimEnsembleSurfaceInView::name() const
{
if ( m_ensembleSurface ) return m_ensembleSurface->uiName();
return "";
}
//--------------------------------------------------------------------------------------------------
///
//--------------------------------------------------------------------------------------------------
RimEnsembleSurface* RimEnsembleSurfaceInView::ensembleSurface() const
{
return m_ensembleSurface;
}
//--------------------------------------------------------------------------------------------------
///
//--------------------------------------------------------------------------------------------------
void RimEnsembleSurfaceInView::setEnsembleSurface( RimEnsembleSurface* surfcoll )
{
m_ensembleSurface = surfcoll;
}
//--------------------------------------------------------------------------------------------------
///
//--------------------------------------------------------------------------------------------------
void RimEnsembleSurfaceInView::updateAllViewItems()
{
syncSurfacesWithView();
updateConnectedEditors();
}
//--------------------------------------------------------------------------------------------------
///
//--------------------------------------------------------------------------------------------------
void RimEnsembleSurfaceInView::syncSurfacesWithView()
{
// Delete surfaceInView without any real Surface connection
std::vector<RimSurfaceInView*> surfsInView = m_surfacesInView.childObjects();
for ( auto surf : surfsInView )
{
if ( !surf->surface() )
{
m_surfacesInView.removeChildObject( surf );
delete surf;
}
}
// Create new surfade entries and reorder
std::vector<RimSurfaceInView*> orderedSurfs;
if ( m_ensembleSurface )
{
// pick up the surfaces and the order from the surface collection
std::vector<RimSurface*> surfs = m_ensembleSurface->surfaces();
for ( auto surf : surfs )
{
// check if this is a surface we need to create
RimSurfaceInView* viewSurf = this->getSurfaceInViewForSurface( surf );
if ( viewSurf == nullptr )
{
RimSurfaceInView* newSurfInView = new RimSurfaceInView();
newSurfInView->setSurface( surf );
orderedSurfs.push_back( newSurfInView );
}
else
{
orderedSurfs.push_back( viewSurf );
}
}
// make sure our view surfaces have the same order as the source surface collection
m_surfacesInView.clear();
for ( auto viewSurf : orderedSurfs )
{
m_surfacesInView.push_back( viewSurf );
}
}
}
//--------------------------------------------------------------------------------------------------
///
//--------------------------------------------------------------------------------------------------
void RimEnsembleSurfaceInView::loadData()
{
for ( RimSurfaceInView* surf : m_surfacesInView )
{
if ( surf->isActive() )
{
surf->loadDataAndUpdate();
}
}
}
//--------------------------------------------------------------------------------------------------
///
//--------------------------------------------------------------------------------------------------
void RimEnsembleSurfaceInView::clearGeometry()
{
for ( RimSurfaceInView* surf : m_surfacesInView )
{
surf->clearGeometry();
}
}
//--------------------------------------------------------------------------------------------------
///
//--------------------------------------------------------------------------------------------------
void RimEnsembleSurfaceInView::appendPartsToModel( cvf::ModelBasicList* model, cvf::Transform* scaleTransform )
{
if ( !isChecked() ) return;
for ( RimSurfaceInView* surf : m_surfacesInView )
{
if ( surf->isActive() )
{
surf->surfacePartMgr()->appendIntersectionGeometryPartsToModel( model, scaleTransform );
}
}
model->updateBoundingBoxesRecursive();
}
//--------------------------------------------------------------------------------------------------
///
//--------------------------------------------------------------------------------------------------
void RimEnsembleSurfaceInView::fieldChangedByUi( const caf::PdmFieldHandle* changedField,
const QVariant& oldValue,
const QVariant& newValue )
{
this->updateUiIconFromToggleField();
if ( changedField == &m_isChecked )
{
RimGridView* ownerView;
this->firstAncestorOrThisOfTypeAsserted( ownerView );
ownerView->scheduleCreateDisplayModelAndRedraw();
}
}
//--------------------------------------------------------------------------------------------------
///
//--------------------------------------------------------------------------------------------------
void RimEnsembleSurfaceInView::initAfterRead()
{
this->updateUiIconFromToggleField();
}
//--------------------------------------------------------------------------------------------------
///
//--------------------------------------------------------------------------------------------------
RimSurfaceInView* RimEnsembleSurfaceInView::getSurfaceInViewForSurface( const RimSurface* surf ) const
{
for ( auto surfInView : m_surfacesInView )
{
if ( surfInView->surface() == surf )
{
return surfInView;
}
}
return nullptr;
}
//--------------------------------------------------------------------------------------------------
///
//--------------------------------------------------------------------------------------------------
void RimEnsembleSurfaceInView::updateCellResultColor( bool hasGeneralCellResult, size_t timeStepIndex )
{
if ( !this->isChecked() ) return;
for ( RimSurfaceInView* surf : m_surfacesInView )
{
if ( surf->isActive() )
{
bool useNativeSurfaceColors = false;
if ( surf->isNativeSurfaceResultsActive() ) useNativeSurfaceColors = true;
if ( !useNativeSurfaceColors )
{
bool showResults = surf->activeSeparateResultDefinition()
? surf->activeSeparateResultDefinition()->hasResult()
: hasGeneralCellResult;
if ( showResults )
{
surf->surfacePartMgr()->updateCellResultColor( timeStepIndex );
}
else
{
useNativeSurfaceColors = true;
}
}
if ( useNativeSurfaceColors )
{
surf->surfacePartMgr()->updateNativeSurfaceColors();
}
}
}
}
//--------------------------------------------------------------------------------------------------
///
//--------------------------------------------------------------------------------------------------
void RimEnsembleSurfaceInView::applySingleColorEffect()
{
if ( !this->isChecked() ) return;
for ( RimSurfaceInView* surf : m_surfacesInView )
{
if ( surf->isActive() )
{
surf->surfacePartMgr()->updateNativeSurfaceColors();
}
}
}
//--------------------------------------------------------------------------------------------------
///
//--------------------------------------------------------------------------------------------------
bool RimEnsembleSurfaceInView::hasAnyActiveSeparateResults()
{
if ( !this->isChecked() ) return false;
for ( RimSurfaceInView* surf : m_surfacesInView )
{
if ( surf->isActive() && surf->activeSeparateResultDefinition() &&
surf->activeSeparateResultDefinition()->hasResult() )
{
return true;
}
}
return false;
}
//--------------------------------------------------------------------------------------------------
///
//--------------------------------------------------------------------------------------------------
void RimEnsembleSurfaceInView::updateLegendRangesTextAndVisibility( RiuViewer* nativeOrOverrideViewer,
bool isUsingOverrideViewer )
{
for ( RimSurfaceInView* surf : m_surfacesInView )
{
surf->updateLegendRangesTextAndVisibility( nativeOrOverrideViewer, isUsingOverrideViewer );
}
}
//--------------------------------------------------------------------------------------------------
///
//--------------------------------------------------------------------------------------------------
std::vector<RimRegularLegendConfig*> RimEnsembleSurfaceInView::legendConfigs()
{
std::vector<RimRegularLegendConfig*> configs;
for ( RimSurfaceInView* surf : m_surfacesInView )
{
if ( surf->isActive() && surf->surfaceResultDefinition() )
{
configs.push_back( surf->surfaceResultDefinition()->legendConfig() );
}
}
return configs;
}

View File

@@ -0,0 +1,86 @@
/////////////////////////////////////////////////////////////////////////////////
//
// Copyright (C) 2021- Equinor ASA
//
// ResInsight is free software: you can redistribute it and/or modify
// it under the terms of the GNU General Public License as published by
// the Free Software Foundation, either version 3 of the License, or
// (at your option) any later version.
//
// ResInsight is distributed in the hope that it will be useful, but WITHOUT ANY
// WARRANTY; without even the implied warranty of MERCHANTABILITY or
// FITNESS FOR A PARTICULAR PURPOSE.
//
// See the GNU General Public License at <http://www.gnu.org/licenses/gpl.html>
// for more details.
//
/////////////////////////////////////////////////////////////////////////////////
#pragma once
#include "RimCheckableNamedObject.h"
#include "cafPdmChildArrayField.h"
#include "cafPdmField.h"
#include "cafPdmObject.h"
#include "cafPdmProxyValueField.h"
#include "cafPdmPtrField.h"
namespace cvf
{
class ModelBasicList;
class Transform;
class ScalarMapper;
} // namespace cvf
class RimSurfaceInView;
class RimSurface;
class RimSurfaceCollection;
class RimEnsembleSurfaceInView;
class RimEnsembleSurface;
class RimRegularLegendConfig;
class RiuViewer;
class RivIntersectionGeometryGeneratorIF;
class RimEnsembleSurfaceInView : public RimCheckableNamedObject
{
CAF_PDM_HEADER_INIT;
public:
RimEnsembleSurfaceInView();
~RimEnsembleSurfaceInView() override;
QString name() const override;
RimEnsembleSurface* ensembleSurface() const;
void setEnsembleSurface( RimEnsembleSurface* surfcoll );
void updateFromSurfaceCollection();
void loadData();
void clearGeometry();
void appendPartsToModel( cvf::ModelBasicList* surfaceVizModel, cvf::Transform* scaleTransform );
void updateCellResultColor( bool hasGeneralCellResult, size_t timeStepIndex );
void applySingleColorEffect();
bool hasAnyActiveSeparateResults();
void updateLegendRangesTextAndVisibility( RiuViewer* nativeOrOverrideViewer, bool isUsingOverrideViewer );
std::vector<RimRegularLegendConfig*> legendConfigs();
void updateAllViewItems();
protected:
void initAfterRead() override;
caf::PdmFieldHandle* userDescriptionField() override;
private:
void fieldChangedByUi( const caf::PdmFieldHandle* changedField, const QVariant& oldValue, const QVariant& newValue ) override;
RimSurfaceInView* getSurfaceInViewForSurface( const RimSurface* surf ) const;
void syncSurfacesWithView();
caf::PdmProxyValueField<QString> m_ensembleSurfaceName;
caf::PdmChildArrayField<RimSurfaceInView*> m_surfacesInView;
caf::PdmPtrField<RimEnsembleSurface*> m_ensembleSurface;
};

View File

@@ -18,17 +18,19 @@
#include "RimGridCaseSurface.h"
#include "RigMainGrid.h"
#include "RigReservoirGridTools.h"
#include "RigSurface.h"
#include "RigMainGrid.h"
#include "RimCase.h"
#include "RimEclipseCase.h"
#include "RimSurfaceCollection.h"
#include "RimTools.h"
#include "cafPdmFieldScriptingCapability.h"
#include "cafPdmObjectScriptingCapability.h"
#include "cafPdmUiSliderEditor.h"
#include "RigReservoirGridTools.h"
#include "cvfVector3.h"
CAF_PDM_SOURCE_INIT( RimGridCaseSurface, "GridCaseSurface" );
@@ -38,11 +40,11 @@ CAF_PDM_SOURCE_INIT( RimGridCaseSurface, "GridCaseSurface" );
//--------------------------------------------------------------------------------------------------
RimGridCaseSurface::RimGridCaseSurface()
{
CAF_PDM_InitObject( "Surface", ":/ReservoirSurface16x16.png", "", "" );
CAF_PDM_InitScriptableObject( "Surface", ":/ReservoirSurface16x16.png", "", "" );
CAF_PDM_InitFieldNoDefault( &m_case, "SourceCase", "Source Case", "", "", "" );
CAF_PDM_InitScriptableFieldNoDefault( &m_case, "SourceCase", "Source Case", "", "", "" );
CAF_PDM_InitField( &m_oneBasedSliceIndex, "SliceIndex", 1, "Slice Index (K)", "", "", "" );
CAF_PDM_InitScriptableField( &m_oneBasedSliceIndex, "SliceIndex", 1, "Slice Index (K)", "", "", "" );
m_oneBasedSliceIndex.uiCapability()->setUiEditorTypeName( caf::PdmUiSliderEditor::uiEditorTypeName() );
}

View File

@@ -71,11 +71,12 @@ protected:
virtual bool updateSurfaceData() = 0;
virtual void clearCachedNativeData() = 0;
protected:
cvf::ref<RigSurface> m_surfaceData;
private:
caf::PdmField<QString> m_userDescription;
caf::PdmField<cvf::Color3f> m_color;
caf::PdmField<double> m_depthOffset;
caf::PdmProxyValueField<QString> m_nameProxy;
cvf::ref<RigSurface> m_surfaceData;
};

View File

@@ -21,6 +21,7 @@
#include "RiaColorTables.h"
#include "RiaLogging.h"
#include "RimEnsembleSurface.h"
#include "RimFileSurface.h"
#include "RimGridCaseSurface.h"
#include "RimGridView.h"
@@ -57,6 +58,9 @@ RimSurfaceCollection::RimSurfaceCollection()
CAF_PDM_InitScriptableFieldNoDefault( &m_surfaces, "SurfacesField", "Surfaces", "", "", "" );
m_surfaces.uiCapability()->setUiTreeHidden( true );
CAF_PDM_InitScriptableFieldNoDefault( &m_ensembleSurfaces, "EnsembleSurfaces", "Ensemble Surfaces", "", "", "" );
m_ensembleSurfaces.uiCapability()->setUiTreeHidden( true );
setDeletable( true );
}
@@ -108,6 +112,14 @@ void RimSurfaceCollection::addSurface( RimSurface* surface )
m_surfaces.push_back( surface );
}
//--------------------------------------------------------------------------------------------------
///
//--------------------------------------------------------------------------------------------------
void RimSurfaceCollection::addEnsembleSurface( RimEnsembleSurface* ensembleSurface )
{
m_ensembleSurfaces.push_back( ensembleSurface );
}
//--------------------------------------------------------------------------------------------------
///
//--------------------------------------------------------------------------------------------------
@@ -212,13 +224,11 @@ RimSurface* RimSurfaceCollection::copySurfaces( std::vector<RimSurface*> surface
//--------------------------------------------------------------------------------------------------
///
//--------------------------------------------------------------------------------------------------
RimSurface* RimSurfaceCollection::addGridCaseSurface( RimCase* sourceCase )
RimSurface* RimSurfaceCollection::addGridCaseSurface( RimCase* sourceCase, int oneBasedSliceIndex )
{
auto s = new RimGridCaseSurface;
s->setCase( sourceCase );
int oneBasedSliceIndex = 1;
s->setOneBasedIndex( oneBasedSliceIndex );
s->setUserDescription( "Surface" );
@@ -255,6 +265,14 @@ std::vector<RimSurfaceCollection*> RimSurfaceCollection::subCollections() const
return m_subCollections.childObjects();
}
//--------------------------------------------------------------------------------------------------
///
//--------------------------------------------------------------------------------------------------
std::vector<RimEnsembleSurface*> RimSurfaceCollection::ensembleSurfaces() const
{
return m_ensembleSurfaces.childObjects();
}
//--------------------------------------------------------------------------------------------------
///
//--------------------------------------------------------------------------------------------------
@@ -264,6 +282,11 @@ void RimSurfaceCollection::loadData()
{
surf->loadDataIfRequired();
}
for ( auto ensSurf : m_ensembleSurfaces )
{
ensSurf->loadDataAndUpdate();
}
}
//--------------------------------------------------------------------------------------------------
@@ -477,6 +500,12 @@ bool RimSurfaceCollection::containsSurface()
{
containsSurface |= coll->containsSurface();
}
for ( auto ensSurf : m_ensembleSurfaces )
{
containsSurface |= ( ensSurf->surfaces().size() > 0 );
}
return containsSurface;
}

View File

@@ -23,6 +23,7 @@
#include "cafPdmObject.h"
class RimSurface;
class RimEnsembleSurface;
class RimCase;
class RimSurfaceCollection : public caf::PdmObject
@@ -36,8 +37,10 @@ public:
void addSurface( RimSurface* surface );
void setAsTopmostFolder();
void addEnsembleSurface( RimEnsembleSurface* ensembleSurface );
RimSurface* importSurfacesFromFiles( const QStringList& fileNames, bool showLegend = true );
RimSurface* addGridCaseSurface( RimCase* sourceCase );
RimSurface* addGridCaseSurface( RimCase* sourceCase, int oneBasedSliceIndex = 1 );
RimSurface* copySurfaces( std::vector<RimSurface*> surfaces );
RimSurface* addSurfacesAtIndex( int index, std::vector<RimSurface*> surfaces );
@@ -64,6 +67,7 @@ public:
std::vector<RimSurface*> surfaces() const;
std::vector<RimSurfaceCollection*> subCollections() const;
std::vector<RimEnsembleSurface*> ensembleSurfaces() const;
protected:
caf::PdmFieldHandle* userDescriptionField() override;
@@ -74,4 +78,5 @@ private:
caf::PdmField<QString> m_collectionName;
caf::PdmChildArrayField<RimSurface*> m_surfaces;
caf::PdmChildArrayField<RimSurfaceCollection*> m_subCollections;
caf::PdmChildArrayField<RimEnsembleSurface*> m_ensembleSurfaces;
};

View File

@@ -18,6 +18,7 @@
#include "RimSurfaceInViewCollection.h"
#include "RimEnsembleSurfaceInView.h"
#include "RimGridView.h"
#include "RimIntersectionResultDefinition.h"
#include "RimOilField.h"
@@ -56,6 +57,9 @@ RimSurfaceInViewCollection::RimSurfaceInViewCollection()
CAF_PDM_InitFieldNoDefault( &m_surfacesInView, "SurfacesInViewField", "SurfacesInViewField", "", "", "" );
m_surfacesInView.uiCapability()->setUiTreeHidden( true );
CAF_PDM_InitFieldNoDefault( &m_ensembleSurfacesInView, "EnsemblesSurfacesInView", "EnsembleSurfacesInView", "", "", "" );
m_ensembleSurfacesInView.uiCapability()->setUiTreeHidden( true );
CAF_PDM_InitFieldNoDefault( &m_surfaceCollection, "SurfaceCollectionRef", "SurfaceCollection", "", "", "" );
m_surfaceCollection.uiCapability()->setUiHidden( true );
@@ -109,6 +113,7 @@ void RimSurfaceInViewCollection::setSurfaceCollection( RimSurfaceCollection* sur
void RimSurfaceInViewCollection::updateAllViewItems()
{
syncCollectionsWithView();
syncEnsembleSurfacesWithView();
syncSurfacesWithView();
updateConnectedEditors();
}
@@ -163,6 +168,56 @@ void RimSurfaceInViewCollection::syncCollectionsWithView()
}
}
//--------------------------------------------------------------------------------------------------
///
//--------------------------------------------------------------------------------------------------
void RimSurfaceInViewCollection::syncEnsembleSurfacesWithView()
{
// check that we have ensemble in view collectinons
std::vector<RimEnsembleSurfaceInView*> ensembleSurfaces = m_ensembleSurfacesInView.childObjects();
for ( auto ensembleSurface : ensembleSurfaces )
{
if ( !ensembleSurface->ensembleSurface() )
{
m_ensembleSurfacesInView.removeChildObject( ensembleSurface );
delete ensembleSurface;
}
}
// Create new collection entries and reorder
std::vector<RimEnsembleSurfaceInView*> orderedEnsembleSurfaces;
if ( m_surfaceCollection )
{
// pick up the collections and the order from the surface collection
std::vector<RimEnsembleSurface*> ensSurfs = m_surfaceCollection->ensembleSurfaces();
for ( auto ensSurf : ensSurfs )
{
// check if this is a collection we need to create
RimEnsembleSurfaceInView* ensembleSurfaceInView = this->getEnsembleSurfaceInViewForEnsembleSurface( ensSurf );
if ( ensembleSurfaceInView == nullptr )
{
RimEnsembleSurfaceInView* newColl = new RimEnsembleSurfaceInView();
newColl->setEnsembleSurface( ensSurf );
orderedEnsembleSurfaces.push_back( newColl );
}
else
{
orderedEnsembleSurfaces.push_back( ensembleSurfaceInView );
}
}
// make sure our view surfaces have the same order as the source surface collection
m_ensembleSurfacesInView.clear();
for ( auto ensSurf : orderedEnsembleSurfaces )
{
m_ensembleSurfacesInView.push_back( ensSurf );
ensSurf->updateAllViewItems();
}
}
}
//--------------------------------------------------------------------------------------------------
///
//--------------------------------------------------------------------------------------------------
@@ -231,6 +286,11 @@ void RimSurfaceInViewCollection::loadData()
coll->loadData();
}
for ( RimEnsembleSurfaceInView* ensSurf : m_ensembleSurfacesInView )
{
ensSurf->loadData();
}
for ( RimSurfaceInView* surf : m_surfacesInView )
{
if ( surf->isActive() )
@@ -250,6 +310,11 @@ void RimSurfaceInViewCollection::clearGeometry()
coll->clearGeometry();
}
for ( RimEnsembleSurfaceInView* ensSurf : m_ensembleSurfacesInView )
{
ensSurf->clearGeometry();
}
for ( RimSurfaceInView* surf : m_surfacesInView )
{
surf->clearGeometry();
@@ -271,6 +336,14 @@ void RimSurfaceInViewCollection::appendPartsToModel( cvf::ModelBasicList* model,
}
}
for ( RimEnsembleSurfaceInView* ensSurf : m_ensembleSurfacesInView )
{
if ( ensSurf->isChecked() )
{
ensSurf->appendPartsToModel( model, scaleTransform );
}
}
for ( RimSurfaceInView* surf : m_surfacesInView )
{
if ( surf->isActive() )
@@ -340,6 +413,23 @@ RimSurfaceInViewCollection*
return nullptr;
}
//--------------------------------------------------------------------------------------------------
///
//--------------------------------------------------------------------------------------------------
RimEnsembleSurfaceInView*
RimSurfaceInViewCollection::getEnsembleSurfaceInViewForEnsembleSurface( const RimEnsembleSurface* coll ) const
{
for ( auto collInView : m_ensembleSurfacesInView )
{
if ( collInView->ensembleSurface() == coll )
{
return collInView;
}
}
return nullptr;
}
//--------------------------------------------------------------------------------------------------
///
//--------------------------------------------------------------------------------------------------

View File

@@ -35,6 +35,8 @@ class ScalarMapper;
class RimSurfaceInView;
class RimSurface;
class RimSurfaceCollection;
class RimEnsembleSurfaceInView;
class RimEnsembleSurface;
class RimRegularLegendConfig;
class RiuViewer;
class RivIntersectionGeometryGeneratorIF;
@@ -76,13 +78,17 @@ private:
RimSurfaceInView* getSurfaceInViewForSurface( const RimSurface* surf ) const;
RimSurfaceInViewCollection* getCollectionInViewForCollection( const RimSurfaceCollection* coll ) const;
RimEnsembleSurfaceInView* getEnsembleSurfaceInViewForEnsembleSurface( const RimEnsembleSurface* coll ) const;
void updateAllViewItems();
void syncCollectionsWithView();
void syncSurfacesWithView();
void syncEnsembleSurfacesWithView();
caf::PdmProxyValueField<QString> m_collectionName;
caf::PdmChildArrayField<RimSurfaceInViewCollection*> m_collectionsInView;
caf::PdmChildArrayField<RimSurfaceInView*> m_surfacesInView;
caf::PdmPtrField<RimSurfaceCollection*> m_surfaceCollection;
caf::PdmChildArrayField<RimEnsembleSurfaceInView*> m_ensembleSurfacesInView;
caf::PdmPtrField<RimSurfaceCollection*> m_surfaceCollection;
};