From 75bcf7dcf4e503821ac60757b842825b003e851e Mon Sep 17 00:00:00 2001 From: Rebecca Cox Date: Mon, 26 Feb 2018 08:36:21 +0100 Subject: [PATCH] #2527 Mohr Circle: Add friction-cohesion line --- .../UserInterface/RiuMohrsCirclePlot.cpp | 92 ++++++++++++++++++- .../UserInterface/RiuMohrsCirclePlot.h | 16 +++- 2 files changed, 105 insertions(+), 3 deletions(-) diff --git a/ApplicationCode/UserInterface/RiuMohrsCirclePlot.cpp b/ApplicationCode/UserInterface/RiuMohrsCirclePlot.cpp index 43c9817b3b..a3f551d2d3 100644 --- a/ApplicationCode/UserInterface/RiuMohrsCirclePlot.cpp +++ b/ApplicationCode/UserInterface/RiuMohrsCirclePlot.cpp @@ -36,11 +36,14 @@ #include #include +#include "qwt_plot_curve.h" #include "qwt_plot_layout.h" #include "qwt_plot_marker.h" #include "qwt_plot_rescaler.h" #include "qwt_plot_shapeitem.h" +#include + //================================================================================================== /// /// \class RiuMohrsCirclePlot @@ -84,11 +87,12 @@ void RiuMohrsCirclePlot::setPrincipals(double p1, double p2, double p3) //-------------------------------------------------------------------------------------------------- /// //-------------------------------------------------------------------------------------------------- -void RiuMohrsCirclePlot::setPrincipalsAndRedrawCircles(double p1, double p2, double p3) +void RiuMohrsCirclePlot::setPrincipalsAndRedrawPlot(double p1, double p2, double p3) { setPrincipals(p1, p2, p3); redrawCircles(); + redrawEnvelope(); } //-------------------------------------------------------------------------------------------------- @@ -126,6 +130,8 @@ void RiuMohrsCirclePlot::updateOnSelectionChanged(const RiuSelectionItem* select void RiuMohrsCirclePlot::clearPlot() { deleteCircles(); + deleteEnvelope(); + this->replot(); } @@ -234,6 +240,68 @@ void RiuMohrsCirclePlot::deleteCircles() m_circlePlotItems.clear(); } +//-------------------------------------------------------------------------------------------------- +/// +//-------------------------------------------------------------------------------------------------- +void RiuMohrsCirclePlot::redrawEnvelope() +{ + deleteEnvelope(); + + if (m_cohesion == HUGE_VAL || m_frictionAngle == HUGE_VAL) + { + this->replot(); + return; + } + + QwtPlotCurve* qwtCurve = new QwtPlotCurve(); + + std::vector xVals; + std::vector yVals; + + double tanFrictionAngle = cvf::Math::abs(cvf::Math::tan(cvf::Math::toRadians(m_frictionAngle))); + + double x = m_cohesion/tanFrictionAngle; + if (m_principal1 < 0) + { + xVals.push_back(-x); + } + else + { + xVals.push_back(x); + } + + xVals.push_back(m_principal1*1.1); + + yVals.push_back(0); + yVals.push_back((x + cvf::Math::abs(m_principal1) * 1.1) * tanFrictionAngle); + + qwtCurve->setSamples(xVals.data(), yVals.data(), 2); + + qwtCurve->setStyle(QwtPlotCurve::Lines); + qwtCurve->setRenderHint(QwtPlotItem::RenderAntialiased, true); + + const QPen curvePen(Qt::red); + qwtCurve->setPen(curvePen); + + qwtCurve->attach(this); + + m_envolopePlotItem = qwtCurve; + this->replot(); +} + +//-------------------------------------------------------------------------------------------------- +/// +//-------------------------------------------------------------------------------------------------- +void RiuMohrsCirclePlot::deleteEnvelope() +{ + if (m_envolopePlotItem) + { + m_envolopePlotItem->detach(); + delete m_envolopePlotItem; + m_envolopePlotItem = nullptr; + } +} + //-------------------------------------------------------------------------------------------------- /// //-------------------------------------------------------------------------------------------------- @@ -272,7 +340,7 @@ void RiuMohrsCirclePlot::queryDataAndUpdatePlot(RimGeoMechView* geoMechView, siz cvf::Vec3f principalDirs[3]; cvf::Vec3f elmPrincipals = elmTensor.calculatePrincipals(principalDirs); - setPrincipalsAndRedrawCircles(elmPrincipals[0], elmPrincipals[1], elmPrincipals[2]); + setPrincipalsAndRedrawPlot(elmPrincipals[0], elmPrincipals[1], elmPrincipals[2]); } //-------------------------------------------------------------------------------------------------- @@ -300,6 +368,10 @@ void RiuMohrsCirclePlot::setDefaults() lineYPlotMarker->setLineStyle(QwtPlotMarker::VLine); lineYPlotMarker->setXValue(0); lineYPlotMarker->attach(this); + + m_envolopePlotItem = nullptr; + m_cohesion = HUGE_VAL; + m_frictionAngle = HUGE_VAL; } //-------------------------------------------------------------------------------------------------- @@ -319,3 +391,19 @@ void RiuMohrsCirclePlot::createMohrCircles() m_mohrCircles[2].radius = (m_principal1 - m_principal2) / 2.0; m_mohrCircles[2].centerX = (m_principal1 + m_principal2) / 2.0; } + +//-------------------------------------------------------------------------------------------------- +/// +//-------------------------------------------------------------------------------------------------- +void RiuMohrsCirclePlot::setFrictionAngle(double frictionAngle) +{ + m_frictionAngle = frictionAngle; +} + +//-------------------------------------------------------------------------------------------------- +/// +//-------------------------------------------------------------------------------------------------- +void RiuMohrsCirclePlot::setCohesion(double cohesion) +{ + m_cohesion = cohesion; +} diff --git a/ApplicationCode/UserInterface/RiuMohrsCirclePlot.h b/ApplicationCode/UserInterface/RiuMohrsCirclePlot.h index 6b3506decd..0a7f5cb236 100644 --- a/ApplicationCode/UserInterface/RiuMohrsCirclePlot.h +++ b/ApplicationCode/UserInterface/RiuMohrsCirclePlot.h @@ -28,6 +28,7 @@ class RimGeoMechView; class QwtRoundScaleDraw; class QwtPlotRescaler; class QWidget; +class QwtPlotCurve; //================================================================================================== // @@ -43,7 +44,7 @@ public: ~RiuMohrsCirclePlot(); void setPrincipals(double p1, double p2, double p3); - void setPrincipalsAndRedrawCircles(double p1, double p2, double p3); + void setPrincipalsAndRedrawPlot(double p1, double p2, double p3); void updateOnSelectionChanged(const RiuSelectionItem* selectionItem); void clearPlot(); @@ -55,6 +56,9 @@ protected: void redrawCircles(); void deleteCircles(); + void redrawEnvelope(); + void deleteEnvelope(); + void queryDataAndUpdatePlot(RimGeoMechView* geoMechView, size_t gridIndex, size_t cellIndex); private: @@ -67,10 +71,14 @@ private: double radius; double centerX; }; + private: void setDefaults(); void createMohrCircles(); + void setFrictionAngle(double frictionAngle); + void setCohesion(double cohesion); + private: double m_principal1; double m_principal2; @@ -79,6 +87,12 @@ private: std::array m_mohrCircles; std::vector m_circlePlotItems; + + QwtPlotCurve* m_envolopePlotItem; + + double m_frictionAngle; + double m_cohesion; + double m_factorOfSafety; QwtPlotRescaler* m_rescaler; };