From 1d0705de467cc34c07fce251ce19fd6b29011dc8 Mon Sep 17 00:00:00 2001 From: Kristian Bendiksen Date: Tue, 19 Jan 2021 10:15:00 +0100 Subject: [PATCH] #7158 Add option to introduce extra well path point at sea level. --- .../ProjectDataModel/RimFileWellPath.cpp | 74 +++++++++++++++++++ .../ProjectDataModel/RimFileWellPath.h | 6 ++ 2 files changed, 80 insertions(+) diff --git a/ApplicationLibCode/ProjectDataModel/RimFileWellPath.cpp b/ApplicationLibCode/ProjectDataModel/RimFileWellPath.cpp index d69f8c4f46..eadfb8c121 100644 --- a/ApplicationLibCode/ProjectDataModel/RimFileWellPath.cpp +++ b/ApplicationLibCode/ProjectDataModel/RimFileWellPath.cpp @@ -1,8 +1,12 @@ #include "RimFileWellPath.h" #include "RicfCommandObject.h" + #include "RifWellPathImporter.h" + +#include "RimProject.h" #include "RimTools.h" + #include "cafUtils.h" #include "QDir" @@ -48,6 +52,14 @@ RimFileWellPath::RimFileWellPath() CAF_PDM_InitField( &m_wellPathIndexInFile, "WellPathNumberInFile", -1, "Well Number in File", "", "", "" ); m_wellPathIndexInFile.uiCapability()->setUiReadOnly( true ); + + CAF_PDM_InitField( &m_useAutoGeneratedPointAtSeaLevel, + "UseAutoGeneratedPointAtSeaLevel", + false, + "Generate Point at Sea Level", + "", + "", + "" ); } //-------------------------------------------------------------------------------------------------- @@ -115,6 +127,8 @@ void RimFileWellPath::defineUiOrdering( QString uiConfigName, caf::PdmUiOrdering { RimWellPath::defineUiOrdering( uiConfigName, uiOrdering ); + uiOrdering.add( &m_useAutoGeneratedPointAtSeaLevel ); + caf::PdmUiGroup* fileInfoGroup = uiOrdering.createGroupBeforeGroup( "Simulation Well", "File" ); if ( isStoredInCache() ) @@ -166,6 +180,11 @@ bool RimFileWellPath::readWellPathFile( QString* errorMessage, RifWellPathImport setSurveyType( wellMetaData.m_surveyType ); updateDate = wellMetaData.m_updateDate.toString( "d MMMM yyyy" ); + if ( m_useAutoGeneratedPointAtSeaLevel ) + { + ensureWellPathStartAtSeaLevel( wellData.m_wellPathGeometry.p() ); + } + setWellPathGeometry( wellData.m_wellPathGeometry.p() ); // Now that the data is read, we know if this is an SSIHUB wellpath that needs to be stored in the @@ -275,3 +294,58 @@ void RimFileWellPath::updateFilePathsFromProjectPath( const QString& newProjectP m_filePathInCache = newCacheFileName; } } + +//-------------------------------------------------------------------------------------------------- +/// +//-------------------------------------------------------------------------------------------------- +void RimFileWellPath::ensureWellPathStartAtSeaLevel( RigWellPath* wellPath ) +{ + std::vector wellPathPoints = wellPath->wellPathPoints(); + std::vector measuredDepths = wellPath->measuredDepths(); + if ( wellPathPoints.empty() || measuredDepths.empty() || wellPathPoints.size() != measuredDepths.size() ) return; + + cvf::Vec3d firstPoint = wellPathPoints[0]; + const double epsilon = 1e-3; + bool firstPointAtSeaLevel = std::abs( firstPoint.z() ) < epsilon; + if ( !firstPointAtSeaLevel ) + { + // Insert a new point on sea level straight above the + // first point in the read well path. + std::vector newPoints = { cvf::Vec3d( firstPoint.x(), firstPoint.y(), 0.0 ) }; + newPoints.insert( newPoints.end(), wellPathPoints.begin(), wellPathPoints.end() ); + wellPath->setWellPathPoints( newPoints ); + + // Give the new point zero measured depth. + std::vector newMeasuredDepths = { 0.0 }; + + // And adjust measured depths of the read data + // with the diff between the old and new first point. + double diffMd = std::abs( newPoints[1].z() - newPoints[0].z() ); + for ( double originalMd : measuredDepths ) + { + newMeasuredDepths.push_back( originalMd + diffMd ); + } + + wellPath->setMeasuredDepths( newMeasuredDepths ); + } +} + +//-------------------------------------------------------------------------------------------------- +/// +//-------------------------------------------------------------------------------------------------- +void RimFileWellPath::fieldChangedByUi( const caf::PdmFieldHandle* changedField, + const QVariant& oldValue, + const QVariant& newValue ) +{ + RimWellPath::fieldChangedByUi( changedField, oldValue, newValue ); + + if ( changedField == &m_useAutoGeneratedPointAtSeaLevel ) + { + RifWellPathImporter wellPathImporter; + QString errorMessage; + if ( readWellPathFile( &errorMessage, &wellPathImporter, false ) ) + { + RimProject::current()->scheduleCreateDisplayModelAndRedrawAllViews(); + } + } +} diff --git a/ApplicationLibCode/ProjectDataModel/RimFileWellPath.h b/ApplicationLibCode/ProjectDataModel/RimFileWellPath.h index 81b6b5c291..6beb4fc57e 100644 --- a/ApplicationLibCode/ProjectDataModel/RimFileWellPath.h +++ b/ApplicationLibCode/ProjectDataModel/RimFileWellPath.h @@ -34,6 +34,9 @@ public: void updateFilePathsFromProjectPath( const QString& newProjectPath, const QString& oldProjectPath ) override; static QString getCacheDirectoryPath(); +protected: + void fieldChangedByUi( const caf::PdmFieldHandle* changedField, const QVariant& oldValue, const QVariant& newValue ) override; + private: QString surveyType() { return m_surveyType; } void setSurveyType( QString surveyType ); @@ -42,6 +45,8 @@ private: void setupBeforeSave() override; + void ensureWellPathStartAtSeaLevel( RigWellPath* wellPath ); + caf::PdmField m_filePath; caf::PdmField m_filePathInCache; // Used for SSIHUB imported well paths caf::PdmField m_wellPathIndexInFile; // -1 means none. @@ -52,6 +57,7 @@ private: caf::PdmField updateDate; caf::PdmField updateUser; caf::PdmField m_surveyType; + caf::PdmField m_useAutoGeneratedPointAtSeaLevel; void defineUiOrdering( QString uiConfigName, caf::PdmUiOrdering& uiOrdering ) override; };