//-------------------------------------------------------------------------------------------------- /// //-------------------------------------------------------------------------------------------------- void RicWellPathImportCompletionsFileFeature::onActionTriggered(bool isChecked) { RimFishboneWellPathCollection* fishbonesWellPathCollection = RicWellPathImportCompletionsFileFeature::selectedWellPathCollection(); CVF_ASSERT(fishbonesWellPathCollection); // Open dialog box to select well path files RiaApplication* app = RiaApplication::instance(); QString defaultDir = app->lastUsedDialogDirectory("WELLPATH_DIR"); QStringList wellPathFilePaths = QFileDialog::getOpenFileNames(Riu3DMainWindowTools::mainWindowWidget(), "Import Fishbone Laterals", defaultDir, "Well Path Laterals (*.json *.asc *.asci *.ascii *.dev);;All Files (*.*)"); if (wellPathFilePaths.size() < 1) return; // Remember the path to next time app->setLastUsedDialogDirectory("WELLPATH_DIR", QFileInfo(wellPathFilePaths.last()).absolutePath()); fishbonesWellPathCollection->importCompletionsFromFile(wellPathFilePaths); RimWellPathCollection* wellPathCollection; fishbonesWellPathCollection->firstAncestorOrThisOfType(wellPathCollection); if (wellPathCollection) { wellPathCollection->updateConnectedEditors(); } if (app->project()) { app->project()->scheduleCreateDisplayModelAndRedrawAllViews(); } }
//-------------------------------------------------------------------------------------------------- /// //-------------------------------------------------------------------------------------------------- void RicReloadWellPathFormationNamesFeature::onActionTriggered(bool isChecked) { std::vector<RimWellPath*> wellPaths; caf::SelectionManager::instance()->objectsByType(&wellPaths); std::vector<RimWellPathCollection*> wellPathCollections; caf::SelectionManager::instance()->objectsByType(&wellPathCollections); if (wellPaths.size() > 0) { RimWellPathCollection* wellPathCollection; wellPaths[0]->firstAncestorOrThisOfTypeAsserted(wellPathCollection); wellPathCollection->reloadAllWellPathFormations(); } else if (wellPathCollections.size() > 0) { wellPathCollections[0]->reloadAllWellPathFormations(); } RimProject* project = RiaApplication::instance()->project(); if (project) { if (project->mainPlotCollection()) { project->mainPlotCollection->updatePlotsWithFormations(); } } }
//-------------------------------------------------------------------------------------------------- /// //-------------------------------------------------------------------------------------------------- void RicWellPathDeleteFeature::onActionTriggered(bool isChecked) { std::vector<RimWellPath*> objects; caf::SelectionManager::instance()->objectsByType(&objects); if (objects.size() == 0) return; RimWellPath* wellPath = objects[0]; RimWellPathCollection* wellPathCollection = NULL; wellPath->firstAncestorOrThisOfType(wellPathCollection); wellPathCollection->removeWellPath(wellPath);; delete wellPath; wellPathCollection->uiCapability()->updateConnectedEditors(); wellPathCollection->scheduleGeometryRegenAndRedrawViews(); }
//-------------------------------------------------------------------------------------------------- /// //-------------------------------------------------------------------------------------------------- void RicNewPerforationIntervalAtMeasuredDepthFeature::onActionTriggered(bool isChecked) { RiuWellPathSelectionItem* wellPathSelItem = wellPathSelectionItem(); CVF_ASSERT(wellPathSelItem); RimWellPath* wellPath = wellPathSelItem->m_wellpath; CVF_ASSERT(wellPath); if (!RicWellPathsUnitSystemSettingsImpl::ensureHasUnitSystem(wellPath)) return; RimPerforationInterval* perforationInterval = new RimPerforationInterval; double measuredDepth = wellPathSelItem->m_measuredDepth; perforationInterval->setStartAndEndMD(measuredDepth, measuredDepth + 50); wellPath->perforationIntervalCollection()->appendPerforation(perforationInterval); RimWellPathCollection* wellPathCollection = nullptr; wellPath->firstAncestorOrThisOfTypeAsserted(wellPathCollection); wellPathCollection->uiCapability()->updateConnectedEditors(); wellPathCollection->scheduleRedrawAffectedViews(); Riu3DMainWindowTools::selectAsCurrentItem(perforationInterval); }
//-------------------------------------------------------------------------------------------------- /// //-------------------------------------------------------------------------------------------------- void RivWellPathPartMgr::appendStaticGeometryPartsToModel(cvf::ModelBasicList* model, cvf::Vec3d displayModelOffset, double characteristicCellSize, cvf::BoundingBox wellPathClipBoundingBox) { RimWellPathCollection* wellPathCollection = NULL; m_rimWellPath->firstAncestorOrThisOfType(wellPathCollection); if (!wellPathCollection) return; if (m_rimWellPath.isNull()) return; if (wellPathCollection->wellPathVisibility() == RimWellPathCollection::FORCE_ALL_OFF) return; if (wellPathCollection->wellPathVisibility() != RimWellPathCollection::FORCE_ALL_ON && m_rimWellPath->showWellPath() == false ) return; if (m_needsTransformUpdate) { // The pipe geometry needs to be rebuilt on scale change to keep the pipes round buildWellPathParts(displayModelOffset, characteristicCellSize, wellPathClipBoundingBox); } if (m_pipeBranchData.m_surfacePart.notNull()) { model->addPart(m_pipeBranchData.m_surfacePart.p()); } if (m_pipeBranchData.m_centerLinePart.notNull()) { model->addPart(m_pipeBranchData.m_centerLinePart.p()); } if (m_wellLabelPart.notNull()) { model->addPart(m_wellLabelPart.p()); } }
//-------------------------------------------------------------------------------------------------- /// //-------------------------------------------------------------------------------------------------- void RivWellFracturePartMgr::appendGeometryPartsToModel(cvf::ModelBasicList* model, const RimEclipseView& eclView) { if (!m_rimFracture->isChecked() || !eclView.fractureColors()->isChecked()) return; if (!m_rimFracture->fractureTemplate()) return; m_visibleFracturePolygons.clear(); double characteristicCellSize = eclView.ownerCase()->characteristicCellSize(); cvf::Collection<cvf::Part> parts; RimStimPlanFractureTemplate* stimPlanFracTemplate = dynamic_cast<RimStimPlanFractureTemplate*>(m_rimFracture->fractureTemplate()); if (stimPlanFracTemplate) { if (eclView.fractureColors()->stimPlanResultColorType() == RimStimPlanColors::SINGLE_ELEMENT_COLOR) { auto part = createStimPlanElementColorSurfacePart(eclView); if (part.notNull()) parts.push_back(part.p()); } else { auto part = createStimPlanColorInterpolatedSurfacePart(eclView); if (part.notNull()) parts.push_back(part.p()); } if (eclView.fractureColors()->showStimPlanMesh()) { auto part = createStimPlanMeshPart(eclView); if (part.notNull()) parts.push_back(part.p()); } } else { auto part = createEllipseSurfacePart(eclView); if (part.notNull()) parts.push_back(part.p()); } double distanceToCenterLine = 1.0; { RimWellPathCollection* wellPathColl = nullptr; m_rimFracture->firstAncestorOrThisOfType(wellPathColl); if (wellPathColl) { distanceToCenterLine = wellPathColl->wellPathRadiusScaleFactor() * characteristicCellSize; } RimSimWellInView* simWell = nullptr; m_rimFracture->firstAncestorOrThisOfType(simWell); if (simWell) { distanceToCenterLine = simWell->pipeRadius(); } } // Make sure the distance is slightly smaller than the pipe radius to make the pipe is visible through the fracture distanceToCenterLine *= 0.1; if (distanceToCenterLine < 0.03) { distanceToCenterLine = 0.03; } auto fractureMatrix = m_rimFracture->transformMatrix(); if (m_rimFracture->fractureTemplate() && m_rimFracture->fractureTemplate()->orientationType() == RimFractureTemplate::ALONG_WELL_PATH) { cvf::Vec3d partTranslation = distanceToCenterLine * cvf::Vec3d(fractureMatrix.col(2)); for (auto& part : parts) { RivWellFracturePartMgr::addPartAtPositiveAndNegativeTranslation(model, part.p(), partTranslation); } } else { for (auto& part : parts) { model->addPart(part.p()); } } if (m_rimFracture->fractureTemplate()) { // Position the containment mask outside the fracture parts // Always duplicate the containment mask parts { auto maskOfFractureAreasOutsideGrid = createMaskOfFractureOutsideGrid(eclView); if (maskOfFractureAreasOutsideGrid.notNull()) { double scaleFactor = 0.03; if (m_rimFracture->fractureTemplate()->orientationType() == RimFractureTemplate::ALONG_WELL_PATH) { scaleFactor = 2 * distanceToCenterLine; } cvf::Vec3d partTranslation = scaleFactor * cvf::Vec3d(fractureMatrix.col(2)); RivWellFracturePartMgr::addPartAtPositiveAndNegativeTranslation( model, maskOfFractureAreasOutsideGrid.p(), partTranslation); } } if (m_rimFracture->fractureTemplate()->fractureContainment()->isEnabled()) { // Position the containment mask outside the fracture parts // Always duplicate the containment mask parts auto containmentMask = createContainmentMaskPart(eclView); if (containmentMask.notNull()) { double scaleFactor = 0.03; if (m_rimFracture->fractureTemplate() && m_rimFracture->fractureTemplate()->orientationType() == RimFractureTemplate::ALONG_WELL_PATH) { scaleFactor = 2 * distanceToCenterLine; } cvf::Vec3d partTranslation = scaleFactor * cvf::Vec3d(fractureMatrix.col(2)); RivWellFracturePartMgr::addPartAtPositiveAndNegativeTranslation(model, containmentMask.p(), partTranslation); } } } appendFracturePerforationLengthParts(eclView, model); }
//-------------------------------------------------------------------------------------------------- /// //-------------------------------------------------------------------------------------------------- void RicDeleteItemExec::redo() { caf::PdmFieldHandle* field = caf::PdmReferenceHelper::fieldFromReference(m_commandData->m_rootObject, m_commandData->m_pathToField); caf::PdmChildArrayFieldHandle* listField = dynamic_cast<caf::PdmChildArrayFieldHandle*>(field); if (listField) { std::vector<caf::PdmObjectHandle*> children; listField->childObjects(&children); caf::PdmObjectHandle* obj = children[m_commandData->m_indexToObject]; caf::SelectionManager::instance()->removeObjectFromAllSelections(obj); std::vector<caf::PdmObjectHandle*> referringObjects; obj->objectsWithReferringPtrFields(referringObjects); if (m_commandData->m_deletedObjectAsXml().isEmpty()) { m_commandData->m_deletedObjectAsXml = xmlObj(obj)->writeObjectToXmlString(); } delete obj; listField->erase(m_commandData->m_indexToObject); caf::PdmObjectHandle* parentObj = listField->ownerObject(); parentObj->uiCapability()->updateConnectedEditors(); Rim3dView* view = nullptr; parentObj->firstAncestorOrThisOfType(view); // Range Filters RimCellRangeFilterCollection* rangeFilterColl; parentObj->firstAncestorOrThisOfType(rangeFilterColl); if (rangeFilterColl) { rangeFilterColl->updateDisplayModeNotifyManagedViews(nullptr); } // Prop Filter RimEclipsePropertyFilterCollection* eclipsePropColl; parentObj->firstAncestorOrThisOfType(eclipsePropColl); RimGeoMechPropertyFilterCollection* geoMechPropColl; parentObj->firstAncestorOrThisOfType(geoMechPropColl); if (view && (eclipsePropColl || geoMechPropColl)) { view->scheduleGeometryRegen(PROPERTY_FILTERED); view->scheduleCreateDisplayModelAndRedraw(); } // Intersections RimIntersectionCollection* crossSectionColl; parentObj->firstAncestorOrThisOfType(crossSectionColl); if (view && crossSectionColl) { crossSectionColl->syncronize2dIntersectionViews(); view->scheduleCreateDisplayModelAndRedraw(); } else { RimCase* parentCase = dynamic_cast<RimCase*>(parentObj); if ( parentCase ) // A view was deleted. Need to update the list of intersection views { parentCase->intersectionViewCollection()->syncFromExistingIntersections(true); } } // SimWell Fractures RimSimWellInView* simWell; parentObj->firstAncestorOrThisOfType(simWell); if (view && simWell) { view->scheduleCreateDisplayModelAndRedraw(); } RimFractureTemplateCollection* fracTemplateColl; parentObj->firstAncestorOrThisOfType(fracTemplateColl); if (fracTemplateColl) { RimProject* proj = nullptr; parentObj->firstAncestorOrThisOfType(proj); if (proj) { proj->createDisplayModelAndRedrawAllViews(); } std::vector<Rim3dView*> views; proj->allVisibleViews(views); for (Rim3dView* view : views) { if (dynamic_cast<RimEclipseView*>(view)) { view->updateConnectedEditors(); } } } // Well paths RimWellPath* wellPath; parentObj->firstAncestorOrThisOfType(wellPath); if (wellPath) { wellPath->updateConnectedEditors(); } RimWellPathCollection* wellPathColl; parentObj->firstAncestorOrThisOfType(wellPathColl); if (wellPathColl) { wellPathColl->scheduleRedrawAffectedViews(); wellPathColl->uiCapability()->updateConnectedEditors(); } // Update due to deletion of curves (not tracks, handled separatly) RimWellLogPlot* wellLogPlot; parentObj->firstAncestorOrThisOfType(wellLogPlot); if (wellLogPlot) { wellLogPlot->calculateAvailableDepthRange(); wellLogPlot->updateDepthZoom(); } RimWellLogTrack* wellLogPlotTrack; parentObj->firstAncestorOrThisOfType(wellLogPlotTrack); if (wellLogPlotTrack) { wellLogPlotTrack->updateXZoom(); } // Update due to delete plots // Make sure the plot collection disappears with the last plot RimWellLogPlotCollection* wellLogPlotCollection = dynamic_cast<RimWellLogPlotCollection*>(parentObj); if (wellLogPlotCollection) { if (wellLogPlotCollection->wellLogPlots.empty()) { RimProject* project = nullptr; parentObj->firstAncestorOrThisOfType(project); if (project) { project->updateConnectedEditors(); } } } // Linked views RimViewLinkerCollection* viewLinkerCollection = nullptr; parentObj->firstAncestorOrThisOfType(viewLinkerCollection); if (viewLinkerCollection) { viewLinkerCollection->uiCapability()->updateConnectedEditors(); RimProject* project = nullptr; parentObj->firstAncestorOrThisOfType(project); if (project) { // Update visibility of top level Linked Views item in the project tree // Not visible if no views are linked project->uiCapability()->updateConnectedEditors(); } } // Formation names RimFormationNamesCollection* formationNamesCollection; parentObj->firstAncestorOrThisOfType(formationNamesCollection); if (formationNamesCollection) { for(caf::PdmObjectHandle* reffingObj :referringObjects) { RimCase* aCase = dynamic_cast<RimCase*>(reffingObj); if (aCase) aCase->updateFormationNamesData(); } } RimSummaryPlotCollection* summaryPlotCollection = nullptr; parentObj->firstAncestorOrThisOfType(summaryPlotCollection); if (summaryPlotCollection) { summaryPlotCollection->updateSummaryNameHasChanged(); RiuPlotMainWindow* mainPlotWindow = RiaApplication::instance()->mainPlotWindow(); mainPlotWindow->updateSummaryPlotToolBar(); } RimSummaryCrossPlotCollection* summaryCrossPlotCollection = nullptr; parentObj->firstAncestorOrThisOfType(summaryCrossPlotCollection); if (summaryCrossPlotCollection) { RiuPlotMainWindow* mainPlotWindow = RiaApplication::instance()->mainPlotWindow(); mainPlotWindow->updateSummaryPlotToolBar(); } RimEnsembleCurveSetCollection* ensembleCurveSetColl = nullptr; parentObj->firstAncestorOrThisOfType(ensembleCurveSetColl); if (ensembleCurveSetColl) { RimSummaryPlot* plot = nullptr; ensembleCurveSetColl->firstAncestorOrThisOfType(plot); if (plot) plot->updateConnectedEditors(); } } }
//-------------------------------------------------------------------------------------------------- /// The pipe geometry needs to be rebuilt on scale change to keep the pipes round //-------------------------------------------------------------------------------------------------- void RivWellPathPartMgr::buildWellPathParts(cvf::Vec3d displayModelOffset, double characteristicCellSize, cvf::BoundingBox wellPathClipBoundingBox) { RimWellPathCollection* wellPathCollection = NULL; m_rimWellPath->firstAncestorOrThisOfType(wellPathCollection); if (!wellPathCollection) return; RigWellPath* wellPathGeometry = m_rimWellPath->wellPathGeometry(); if (!wellPathGeometry) return; if (wellPathGeometry->m_wellPathPoints.size() < 2) return; clearAllBranchData(); double wellPathRadius = wellPathCollection->wellPathRadiusScaleFactor() * m_rimWellPath->wellPathRadiusScaleFactor() * characteristicCellSize; cvf::Vec3d textPosition = wellPathGeometry->m_wellPathPoints[0]; // Generate the well path geometry as a line and pipe structure { RivPipeBranchData& pbd = m_pipeBranchData; pbd.m_pipeGeomGenerator = new RivPipeGeometryGenerator; pbd.m_pipeGeomGenerator->setRadius(wellPathRadius); pbd.m_pipeGeomGenerator->setCrossSectionVertexCount(wellPathCollection->wellPathCrossSectionVertexCount()); pbd.m_pipeGeomGenerator->setPipeColor( m_rimWellPath->wellPathColor()); cvf::ref<cvf::Vec3dArray> cvfCoords = new cvf::Vec3dArray; if (wellPathCollection->wellPathClip) { size_t firstVisibleSegmentIndex = cvf::UNDEFINED_SIZE_T; for (size_t idx = 0; idx < wellPathGeometry->m_wellPathPoints.size(); idx++) { cvf::Vec3d point = wellPathGeometry->m_wellPathPoints[idx]; if (point.z() < (wellPathClipBoundingBox.max().z() + wellPathCollection->wellPathClipZDistance)) { firstVisibleSegmentIndex = idx; break; } } std::vector<cvf::Vec3d> clippedPoints; if (firstVisibleSegmentIndex != cvf::UNDEFINED_SIZE_T) { for (size_t idx = firstVisibleSegmentIndex; idx < wellPathGeometry->m_wellPathPoints.size(); idx++) { clippedPoints.push_back(wellPathGeometry->m_wellPathPoints[idx]); } pbd.m_pipeGeomGenerator->setFirstSegmentIndex(firstVisibleSegmentIndex); } if (clippedPoints.size() < 2) return; textPosition = clippedPoints[0]; cvfCoords->assign(clippedPoints); } else { cvfCoords->assign(wellPathGeometry->m_wellPathPoints); } // Scale the centerline coordinates using the Z-scale transform of the grid and correct for the display offset. for (size_t cIdx = 0; cIdx < cvfCoords->size(); ++cIdx) { cvf::Vec4d transfCoord = m_scaleTransform->worldTransform() * cvf::Vec4d((*cvfCoords)[cIdx] - displayModelOffset, 1); (*cvfCoords)[cIdx][0] = transfCoord[0]; (*cvfCoords)[cIdx][1] = transfCoord[1]; (*cvfCoords)[cIdx][2] = transfCoord[2]; } pbd.m_pipeGeomGenerator->setPipeCenterCoords(cvfCoords.p()); pbd.m_surfaceDrawable = pbd.m_pipeGeomGenerator->createPipeSurface(); pbd.m_centerLineDrawable = pbd.m_pipeGeomGenerator->createCenterLine(); if (pbd.m_surfaceDrawable.notNull()) { pbd.m_surfacePart = new cvf::Part; pbd.m_surfacePart->setDrawable(pbd.m_surfaceDrawable.p()); RivWellPathSourceInfo* sourceInfo = new RivWellPathSourceInfo(m_rimWellPath); pbd.m_surfacePart->setSourceInfo(sourceInfo); caf::SurfaceEffectGenerator surfaceGen(cvf::Color4f(m_rimWellPath->wellPathColor()), caf::PO_1); cvf::ref<cvf::Effect> eff = surfaceGen.generateCachedEffect(); pbd.m_surfacePart->setEffect(eff.p()); } if (pbd.m_centerLineDrawable.notNull()) { pbd.m_centerLinePart = new cvf::Part; pbd.m_centerLinePart->setDrawable(pbd.m_centerLineDrawable.p()); caf::MeshEffectGenerator gen(m_rimWellPath->wellPathColor()); cvf::ref<cvf::Effect> eff = gen.generateCachedEffect(); pbd.m_centerLinePart->setEffect(eff.p()); } } // Generate label with well-path name textPosition -= displayModelOffset; textPosition.transformPoint(m_scaleTransform->worldTransform()); textPosition.z() += characteristicCellSize; // * m_rimReservoirView->wellCollection()->wellHeadScaleFactor(); textPosition.z() += 1.2 * characteristicCellSize; m_wellLabelPart = NULL; if (wellPathCollection->showWellPathLabel() && m_rimWellPath->showWellPathLabel() && !m_rimWellPath->name().isEmpty()) { cvf::Font* font = RiaApplication::instance()->customFont(); cvf::ref<cvf::DrawableText> drawableText = new cvf::DrawableText; drawableText->setFont(font); drawableText->setCheckPosVisible(false); drawableText->setDrawBorder(false); drawableText->setDrawBackground(false); drawableText->setVerticalAlignment(cvf::TextDrawer::CENTER); drawableText->setTextColor(wellPathCollection->wellPathLabelColor()); cvf::String cvfString = cvfqt::Utils::toString(m_rimWellPath->name()); cvf::Vec3f textCoord(textPosition); drawableText->addText(cvfString, textCoord); cvf::ref<cvf::Part> part = new cvf::Part; part->setName("RivWellHeadPartMgr: text " + cvfString); part->setDrawable(drawableText.p()); cvf::ref<cvf::Effect> eff = new cvf::Effect; part->setEffect(eff.p()); part->setPriority(1000); m_wellLabelPart = part; } m_needsTransformUpdate = false; }