(#869) Summary : Right axis WIP

This commit is contained in:
Magne Sjaastad 2016-10-10 11:05:45 +02:00
parent 6a8801e179
commit c07f13d407
13 changed files with 585 additions and 226 deletions

View File

@ -93,6 +93,7 @@ ${CEE_CURRENT_LIST_DIR}RimSummaryCurveAppearanceCalculator.h
${CEE_CURRENT_LIST_DIR}RimEclipseInputCaseOpm.h
${CEE_CURRENT_LIST_DIR}RimIntersectionBox.h
${CEE_CURRENT_LIST_DIR}RimSummaryYAxisProperties.h
${CEE_CURRENT_LIST_DIR}RimSummaryCurvesCalculator.h
)
set (SOURCE_GROUP_SOURCE_FILES
@ -184,6 +185,7 @@ ${CEE_CURRENT_LIST_DIR}RimSummaryCurveAppearanceCalculator.cpp
${CEE_CURRENT_LIST_DIR}RimEclipseInputCaseOpm.cpp
${CEE_CURRENT_LIST_DIR}RimIntersectionBox.cpp
${CEE_CURRENT_LIST_DIR}RimSummaryYAxisProperties.cpp
${CEE_CURRENT_LIST_DIR}RimSummaryCurvesCalculator.cpp
)
list(APPEND CODE_HEADER_FILES

View File

@ -52,6 +52,16 @@ namespace caf
setDefault(RimDefines::UNIT_METER);
}
template<>
void caf::AppEnum< RimDefines::PlotAxis >::setUp()
{
addItem(RimDefines::PLOT_AXIS_LEFT, "PLOT_AXIS_LEFT", "Left");
addItem(RimDefines::PLOT_AXIS_RIGHT, "PLOT_AXIS_RIGHT", "Right");
setDefault(RimDefines::PLOT_AXIS_LEFT);
}
}

View File

@ -80,5 +80,17 @@ public:
};
static double feetPerMeter() { return 3.2808399; }
// Defines relate to plotting
enum PlotAxis
{
PLOT_AXIS_LEFT,
PLOT_AXIS_RIGHT
};
static double minimumDefaultValuePlot() { return - 10.0; }
static double maximumDefaultValuePlot() { return 100.0; }
};

View File

@ -19,22 +19,28 @@
#include "RimSummaryCurve.h"
#include "RiaApplication.h"
#include "RifReaderEclipseSummary.h"
#include "RigSummaryCaseData.h"
#include "RimDefines.h"
#include "RimEclipseResultCase.h"
#include "RimProject.h"
#include "RimSummaryCase.h"
#include "RimSummaryCurveFilter.h"
#include "RimSummaryFilter.h"
#include "RimSummaryPlot.h"
#include "RimSummaryPlotCollection.h"
#include "RiuLineSegmentQwtPlotCurve.h"
#include "RiuSummaryQwtPlot.h"
#include "cafPdmUiComboBoxEditor.h"
#include "cafPdmUiListEditor.h"
#include "cafPdmUiTreeOrdering.h"
#include "RiuLineSegmentQwtPlotCurve.h"
#include "qwt_date.h"
#include "RimSummaryCase.h"
#include "RigSummaryCaseData.h"
#include "RimSummaryFilter.h"
CAF_PDM_SOURCE_INIT(RimSummaryAddress, "SummaryAddress");
@ -164,6 +170,8 @@ RimSummaryCurve::RimSummaryCurve()
m_curveVariable.uiCapability()->setUiHidden(true);
m_curveVariable.uiCapability()->setUiChildrenHidden(true);
CAF_PDM_InitFieldNoDefault(&m_plotAxis, "PlotAxis", "Axis", "", "", "");
m_curveVariable = new RimSummaryAddress;
// Add some space before name to indicate these belong to the Auto Name field
@ -233,6 +241,35 @@ std::string RimSummaryCurve::unitName()
return "";
}
//--------------------------------------------------------------------------------------------------
///
//--------------------------------------------------------------------------------------------------
std::vector<double> RimSummaryCurve::yPlotValues() const
{
std::vector<QDateTime> dateTimes;
std::vector<double> values;
this->curveData(&dateTimes, &values);
return values;
}
//--------------------------------------------------------------------------------------------------
///
//--------------------------------------------------------------------------------------------------
void RimSummaryCurve::setPlotAxis(RimDefines::PlotAxis plotAxis)
{
m_plotAxis = plotAxis;
}
//--------------------------------------------------------------------------------------------------
///
//--------------------------------------------------------------------------------------------------
RimDefines::PlotAxis RimSummaryCurve::associatedPlotAxis() const
{
return m_plotAxis();
}
//--------------------------------------------------------------------------------------------------
///
//--------------------------------------------------------------------------------------------------
@ -353,6 +390,8 @@ void RimSummaryCurve::onLoadDataAndUpdate()
if (m_parentQwtPlot) m_parentQwtPlot->replot();
}
updateQwtPlotAxis();
}
//--------------------------------------------------------------------------------------------------
@ -382,9 +421,28 @@ void RimSummaryCurve::defineUiOrdering(QString uiConfigName, caf::PdmUiOrdering&
appearanceGroup->add(&m_addCaseNameToCurveName);
}
uiOrdering.add(&m_plotAxis);
uiOrdering.setForgetRemainingFields(true); // For now.
}
//--------------------------------------------------------------------------------------------------
///
//--------------------------------------------------------------------------------------------------
void RimSummaryCurve::updateQwtPlotAxis()
{
if (m_qwtPlotCurve)
{
if (this->associatedPlotAxis() == RimDefines::PLOT_AXIS_LEFT)
{
m_qwtPlotCurve->setYAxis(QwtPlot::yLeft);
}
else
{
m_qwtPlotCurve->setYAxis(QwtPlot::yRight);
}
}
}
//--------------------------------------------------------------------------------------------------
///
@ -393,6 +451,10 @@ void RimSummaryCurve::fieldChangedByUi(const caf::PdmFieldHandle* changedField,
{
this->RimPlotCurve::fieldChangedByUi(changedField,oldValue,newValue);
RimSummaryPlot* plot = nullptr;
firstAncestorOrThisOfType(plot);
CVF_ASSERT(plot);
if(changedField == &m_uiFilterResultSelection)
{
if (0 <= m_uiFilterResultSelection() && static_cast<size_t>(m_uiFilterResultSelection()) < summaryReader()->allResultAddresses().size())
@ -406,27 +468,29 @@ void RimSummaryCurve::fieldChangedByUi(const caf::PdmFieldHandle* changedField,
this->loadDataAndUpdate();
RimSummaryPlot* plot = nullptr;
firstAncestorOrThisOfType(plot);
plot->updateYAxisUnit();
plot->updateLeftAndRightYAxis();
}
else if (&m_showCurve == changedField)
{
RimSummaryPlot* plot = nullptr;
firstAncestorOrThisOfType(plot);
plot->updateYAxisUnit();
plot->updateLeftAndRightYAxis();
}
else if (changedField == &m_addCaseNameToCurveName)
{
this->uiCapability()->updateConnectedEditors();
updateCurveName();
}
else if (changedField == &m_plotAxis)
{
updateQwtPlotAxis();
plot->updateLeftAndRightYAxis();
}
}
//--------------------------------------------------------------------------------------------------
///
//--------------------------------------------------------------------------------------------------
RifReaderEclipseSummary* RimSummaryCurve::summaryReader()
RifReaderEclipseSummary* RimSummaryCurve::summaryReader() const
{
if (!m_summaryCase()) return nullptr;
@ -446,7 +510,7 @@ void RimSummaryCurve::defineUiTreeOrdering(caf::PdmUiTreeOrdering& uiTreeOrderin
//--------------------------------------------------------------------------------------------------
///
//--------------------------------------------------------------------------------------------------
bool RimSummaryCurve::curveData(std::vector<QDateTime>* timeSteps, std::vector<double>* values)
bool RimSummaryCurve::curveData(std::vector<QDateTime>* timeSteps, std::vector<double>* values) const
{
CVF_ASSERT(timeSteps && values);

View File

@ -25,14 +25,16 @@
#include "cafPdmPtrField.h"
#include "cafPdmChildField.h"
#include "RimPlotCurve.h"
#include "RifEclipseSummaryAddress.h"
#include "RimDefines.h"
#include "RimPlotCurve.h"
#include "cafAppEnum.h"
class RimSummaryCase;
class RifReaderEclipseSummary;
class RiuLineSegmentQwtPlotCurve;
class RimSummaryCase;
class RimSummaryFilter;
class RiuLineSegmentQwtPlotCurve;
class RimSummaryAddress: public caf::PdmObject
{
@ -68,6 +70,7 @@ private:
class RimSummaryCurve : public RimPlotCurve
{
CAF_PDM_HEADER_INIT;
public:
RimSummaryCurve();
virtual ~RimSummaryCurve();
@ -79,6 +82,13 @@ public:
RifEclipseSummaryAddress summaryAddress();
void setSummaryAddress(const RifEclipseSummaryAddress& address);
std::string unitName();
std::vector<double> yPlotValues() const;
void setPlotAxis(RimDefines::PlotAxis plotAxis);
RimDefines::PlotAxis associatedPlotAxis() const;
void updateQwtPlotAxis();
protected:
// RimPlotCurve overrides
@ -87,8 +97,8 @@ protected:
virtual void onLoadDataAndUpdate() override;
private:
RifReaderEclipseSummary* summaryReader();
bool curveData(std::vector<QDateTime>* timeSteps, std::vector<double>* values);
RifReaderEclipseSummary* summaryReader() const;
bool curveData(std::vector<QDateTime>* timeSteps, std::vector<double>* values) const;
// Overridden PDM methods
virtual void fieldChangedByUi(const caf::PdmFieldHandle* changedField, const QVariant& oldValue, const QVariant& newValue);
@ -96,15 +106,16 @@ private:
virtual QList<caf::PdmOptionItemInfo> calculateValueOptions(const caf::PdmFieldHandle* fieldNeedingOptions, bool* useOptionsOnly);
virtual void defineUiOrdering(QString uiConfigName, caf::PdmUiOrdering& uiOrdering) override;
private:
// Fields
caf::PdmPtrField<RimSummaryCase*> m_summaryCase;
caf::PdmChildField<RimSummaryAddress*> m_curveVariable;
caf::PdmField<QString> m_selectedVariableDisplayField;
caf::PdmField<bool> m_addCaseNameToCurveName;
caf::PdmField< caf::AppEnum< RimDefines::PlotAxis > > m_plotAxis;
// Filter fields
caf::PdmChildField<RimSummaryFilter*> m_summaryFilter;
caf::PdmField<int> m_uiFilterResultSelection;
};

View File

@ -29,6 +29,8 @@
#include "RimProject.h"
#include "RimSummaryCase.h"
#include "RimSummaryCurve.h"
#include "RimSummaryCurveAppearanceCalculator.h"
#include "RimSummaryFilter.h"
#include "RimSummaryPlot.h"
#include "RimSummaryPlotCollection.h"
@ -37,11 +39,8 @@
#include "WellLogCommands/RicWellLogPlotCurveFeatureImpl.h"
#include "cafPdmUiComboBoxEditor.h"
#include "cafPdmUiListEditor.h"
#include "cafPdmUiPushButtonEditor.h"
#include "cafPdmUiTreeOrdering.h"
#include "RimSummaryCurveAppearanceCalculator.h"
QTextStream& operator << (QTextStream& str, const std::vector<RifEclipseSummaryAddress>& sobj)
@ -114,6 +113,7 @@ RimSummaryCurveFilter::RimSummaryCurveFilter()
CAF_PDM_InitFieldNoDefault(&m_groupAppearanceType, "GroupAppearanceType", "Group", "", "", "");
CAF_PDM_InitFieldNoDefault(&m_regionAppearanceType, "RegionAppearanceType", "Region", "", "", "");
CAF_PDM_InitFieldNoDefault(&m_plotAxis, "PlotAxis", "Axis", "", "", "");
}
//--------------------------------------------------------------------------------------------------
@ -218,7 +218,9 @@ void RimSummaryCurveFilter::defineUiOrdering(QString uiConfigName, caf::PdmUiOrd
m_regionAppearanceType.uiCapability()->setUiReadOnly(m_useAutoAppearanceAssignment);
}
uiOrdering.add(&m_plotAxis);
uiOrdering.add(&m_applyButtonField);
uiOrdering.setForgetRemainingFields(true);
}
@ -239,7 +241,7 @@ void RimSummaryCurveFilter::fieldChangedByUi(const caf::PdmFieldHandle* changedF
RimSummaryPlot* plot = nullptr;
firstAncestorOrThisOfType(plot);
plot->updateYAxisUnit();
plot->updateLeftAndRightYAxis();
}
else if (changedField == &m_showCurves)
{
@ -249,6 +251,18 @@ void RimSummaryCurveFilter::fieldChangedByUi(const caf::PdmFieldHandle* changedF
}
if (m_parentQwtPlot) m_parentQwtPlot->replot();
}
else if (changedField == &m_plotAxis)
{
for (RimSummaryCurve* curve : m_curves)
{
curve->setPlotAxis(m_plotAxis());
curve->updateQwtPlotAxis();
RimSummaryPlot* plot = nullptr;
firstAncestorOrThisOfType(plot);
plot->updateLeftAndRightYAxis();
}
}
}
//--------------------------------------------------------------------------------------------------
@ -493,6 +507,14 @@ void RimSummaryCurveFilter::updateCaseNameHasChanged()
}
//--------------------------------------------------------------------------------------------------
///
//--------------------------------------------------------------------------------------------------
RimDefines::PlotAxis RimSummaryCurveFilter::associatedPlotAxis() const
{
return m_plotAxis();
}
//--------------------------------------------------------------------------------------------------
///
//--------------------------------------------------------------------------------------------------

View File

@ -25,20 +25,26 @@
#include "cafPdmPtrField.h"
#include "cafPdmChildField.h"
#include "cafPdmChildArrayField.h"
#include "RimPlotCurve.h"
#include "RifEclipseSummaryAddress.h"
#include "cafAppEnum.h"
#include "RimSummaryCurve.h"
#include "RimSummaryFilter.h"
#include "cafPdmPtrArrayField.h"
#include "RifEclipseSummaryAddress.h"
#include "RimDefines.h"
#include "RimSummaryCurveAppearanceCalculator.h"
class RimSummaryCase;
#include "qwt_plot.h"
class QwtPlot;
class QwtPlotCurve;
class RifReaderEclipseSummary;
class RimSummaryCase;
class RimSummaryCurve;
class RimSummaryFilter;
class RiuLineSegmentQwtPlotCurve;
#include <QPointer>
Q_DECLARE_METATYPE(RifEclipseSummaryAddress);
//==================================================================================================
@ -48,6 +54,7 @@ Q_DECLARE_METATYPE(RifEclipseSummaryAddress);
class RimSummaryCurveFilter : public caf::PdmObject
{
CAF_PDM_HEADER_INIT;
public:
RimSummaryCurveFilter();
virtual ~RimSummaryCurveFilter();
@ -64,6 +71,8 @@ public:
void updateCaseNameHasChanged();
RimDefines::PlotAxis associatedPlotAxis() const;
private:
void syncCurvesFromUiSelection();
void createCurvesFromCurveDefinitions(const std::set<std::pair<RimSummaryCase*, RifEclipseSummaryAddress> >& curveDefinitions);
@ -90,6 +99,9 @@ private:
caf::PdmChildArrayField<RimSummaryCurve*> m_curves;
caf::PdmField<QString> m_selectedVariableDisplayField;
caf::PdmField< caf::AppEnum< RimDefines::PlotAxis > > m_plotAxis;
// Filter fields
caf::PdmChildField<RimSummaryFilter*> m_summaryFilter;

View File

@ -0,0 +1,290 @@
/////////////////////////////////////////////////////////////////////////////////
//
// Copyright (C) 2016 Statoil 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 "RimSummaryCurvesCalculator.h"
#include "RigStatisticsCalculator.h"
#include "RimDefines.h"
#include "RimSummaryCurve.h"
#include "RimSummaryCurveFilter.h"
#include "RimSummaryYAxisProperties.h"
#include "RiuSummaryQwtPlot.h"
#include "qwt_plot_curve.h"
#include "qwt_scale_draw.h"
#include "qwt_scale_engine.h"
#include <set>
#include <string>
#include <cmath>
//--------------------------------------------------------------------------------------------------
// e format as [-]9.9e[+|-]999
// E format as[-]9.9E[+| -]999
// f format as[-]9.9
// g use e or f format, whichever is the most concise
// G use E or f format, whichever is the most concise
//--------------------------------------------------------------------------------------------------
class DecimalScaleDraw : public QwtScaleDraw
{
public:
virtual QwtText label(double value) const override
{
if (qFuzzyCompare(value + 1.0, 1.0))
value = 0.0;
int precision = DecimalScaleDraw::calculatePrecision(value);
return QString::number(value, 'f', precision);
}
private:
static int calculatePrecision(double value)
{
double absVal = fabs(value);
if (1e-16 < absVal && absVal < 1.0e3)
{
int logVal = static_cast<int>(log10(absVal));
int numDigitsAfterPoint = abs(logVal - 6);
return numDigitsAfterPoint;
}
else
{
return 3;
}
}
};
//--------------------------------------------------------------------------------------------------
///
//--------------------------------------------------------------------------------------------------
class ScientificScaleDraw : public QwtScaleDraw
{
public:
virtual QwtText label(double value) const override
{
if (qFuzzyCompare(value + 1.0, 1.0))
value = 0.0;
return QString::number(value, 'e', 2);
}
};
//--------------------------------------------------------------------------------------------------
///
//--------------------------------------------------------------------------------------------------
RimSummaryCurvesCalculator::RimSummaryCurvesCalculator(RimSummaryYAxisProperties* axisProperties,
const std::vector<RimSummaryCurve*>& curves,
const std::vector<RimSummaryCurveFilter*>& curveFilters)
: m_axisProperties(axisProperties),
m_singleCurves(curves),
m_curveFilters(curveFilters)
{
}
//--------------------------------------------------------------------------------------------------
///
//--------------------------------------------------------------------------------------------------
void RimSummaryCurvesCalculator::applyPropertiesToPlot(RiuSummaryQwtPlot* m_qwtPlot)
{
if (!m_qwtPlot) return;
{
QString axisTitle = m_axisProperties->customTitle;
if (m_axisProperties->isAutoTitle) axisTitle = autoAxisTitle();
QwtText axisTitleY = m_qwtPlot->axisTitle(m_axisProperties->axis());
QFont axisTitleYFont = axisTitleY.font();
axisTitleYFont.setBold(true);
axisTitleYFont.setPixelSize(m_axisProperties->fontSize);
axisTitleY.setFont(axisTitleYFont);
axisTitleY.setText(axisTitle);
m_qwtPlot->setAxisTitle(m_axisProperties->axis(), axisTitleY);
}
{
QFont yAxisFont = m_qwtPlot->axisFont(m_axisProperties->axis());
yAxisFont.setBold(false);
yAxisFont.setPixelSize(m_axisProperties->fontSize);
m_qwtPlot->setAxisFont(m_axisProperties->axis(), yAxisFont);
}
{
if (m_axisProperties->numberFormat == RimSummaryYAxisProperties::NUMBER_FORMAT_AUTO)
{
m_qwtPlot->setAxisScaleDraw(m_axisProperties->axis(), new QwtScaleDraw);
}
else if (m_axisProperties->numberFormat == RimSummaryYAxisProperties::NUMBER_FORMAT_DECIMAL)
{
m_qwtPlot->setAxisScaleDraw(m_axisProperties->axis(), new DecimalScaleDraw);
}
else if (m_axisProperties->numberFormat == RimSummaryYAxisProperties::NUMBER_FORMAT_SCIENTIFIC)
{
m_qwtPlot->setAxisScaleDraw(m_axisProperties->axis(), new ScientificScaleDraw());
}
}
{
if (m_axisProperties->isLogarithmicScaleEnabled)
{
QwtLogScaleEngine* currentScaleEngine = dynamic_cast<QwtLogScaleEngine*>(m_qwtPlot->axisScaleEngine(m_axisProperties->axis()));
if (!currentScaleEngine)
{
m_qwtPlot->setAxisScaleEngine(m_axisProperties->axis(), new QwtLogScaleEngine);
}
}
else
{
QwtLinearScaleEngine* currentScaleEngine = dynamic_cast<QwtLinearScaleEngine*>(m_qwtPlot->axisScaleEngine(m_axisProperties->axis()));
if (!currentScaleEngine)
{
m_qwtPlot->setAxisScaleEngine(m_axisProperties->axis(), new QwtLinearScaleEngine);
}
}
}
{
if (m_axisProperties->isAutoScaleEnabled)
{
double min = HUGE_VAL;
double max = -HUGE_VAL;
computeYRange(&min, &max);
m_qwtPlot->setAxisScale(m_axisProperties->axis(), min, max);
}
else
{
m_qwtPlot->setAxisScale(m_axisProperties->axis(), m_axisProperties->visibleRangeMin, m_axisProperties->visibleRangeMax);
}
}
}
//--------------------------------------------------------------------------------------------------
///
//--------------------------------------------------------------------------------------------------
QString RimSummaryCurvesCalculator::autoAxisTitle() const
{
std::set<std::string> unitNames;
for (RimSummaryCurve* rimCurve : m_singleCurves)
{
if (rimCurve->isCurveVisible()) unitNames.insert(rimCurve->unitName());
}
for (RimSummaryCurveFilter* curveFilter : m_curveFilters)
{
std::set<std::string> filterUnitNames = curveFilter->unitNames();
unitNames.insert(filterUnitNames.begin(), filterUnitNames.end());
}
QString assembledYAxisText;
for (const std::string& unitName : unitNames)
{
assembledYAxisText += "[" + QString::fromStdString(unitName) + "] ";
}
return assembledYAxisText;
}
//--------------------------------------------------------------------------------------------------
///
//--------------------------------------------------------------------------------------------------
void RimSummaryCurvesCalculator::computeYRange(double* min, double* max) const
{
double minValue = HUGE_VAL;
double maxValue = -HUGE_VAL;
for (RimSummaryCurve* curve : m_singleCurves)
{
double minCurveValue = HUGE_VAL;
double maxCurveValue = -HUGE_VAL;
if (curve->isCurveVisible() && curveValueRangeY(curve->qwtPlotCurve(), &minCurveValue, &maxCurveValue))
{
if (minCurveValue < minValue)
{
minValue = minCurveValue;
}
if (maxCurveValue > maxValue)
{
maxValue = maxCurveValue;
}
}
}
if (minValue == HUGE_VAL)
{
minValue = RimDefines::minimumDefaultValuePlot();
maxValue = RimDefines::maximumDefaultValuePlot();
}
if (m_axisProperties->isAutoScaleEnabled && m_axisProperties->isLogarithmicScaleEnabled)
{
// For logarithmic auto scaling, compute positive curve value closest to zero and use
// this value as the plot visible minimum
double pos = HUGE_VAL;
double neg = -HUGE_VAL;
for (RimSummaryCurve* curve : m_singleCurves)
{
if (curve->isCurveVisible())
{
RigStatisticsCalculator::posNegClosestToZero(curve->yPlotValues(), pos, neg);
}
}
if (pos != HUGE_VAL)
{
minValue = pos;
}
}
*min = minValue;
*max = maxValue;
}
//--------------------------------------------------------------------------------------------------
///
//--------------------------------------------------------------------------------------------------
bool RimSummaryCurvesCalculator::curveValueRangeY(const QwtPlotCurve* qwtCurve, double* min, double* max) const
{
if (!qwtCurve) return false;
if (qwtCurve->data()->size() < 1)
{
return false;
}
*min = qwtCurve->minYValue();
*max = qwtCurve->maxYValue();
return true;
}

View File

@ -0,0 +1,51 @@
/////////////////////////////////////////////////////////////////////////////////
//
// Copyright (C) 2016 Statoil 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 <vector>
#include <QString>
class RimSummaryCurve;
class RimSummaryCurveFilter;
class RimSummaryYAxisProperties;
class RiuSummaryQwtPlot;
class QwtPlotCurve;
class RimSummaryCurvesCalculator
{
public:
RimSummaryCurvesCalculator(RimSummaryYAxisProperties* axisProperties,
const std::vector<RimSummaryCurve*>& curves,
const std::vector<RimSummaryCurveFilter*>& curveFilters);
void applyPropertiesToPlot(RiuSummaryQwtPlot* qwtPlot);
private:
QString autoAxisTitle() const;
void computeYRange(double* min, double* max) const;
bool curveValueRangeY(const QwtPlotCurve* qwtCurve, double* min, double* max) const;
private:
RimSummaryYAxisProperties* m_axisProperties;
std::vector<RimSummaryCurve*> m_singleCurves;
std::vector<RimSummaryCurveFilter*> m_curveFilters;
};

View File

@ -22,6 +22,7 @@
#include "RimSummaryCurve.h"
#include "RimSummaryCurveFilter.h"
#include "RimSummaryCurvesCalculator.h"
#include "RimSummaryPlotCollection.h"
#include "RimSummaryYAxisProperties.h"
@ -35,49 +36,8 @@
#include <QDateTime>
#include <QRectF>
#include "qwt_plot_curve.h"
#include "qwt_plot_renderer.h"
#include "qwt_scale_draw.h"
#include "qwt_scale_engine.h"
//--------------------------------------------------------------------------------------------------
// e format as [-]9.9e[+|-]999
// E format as[-]9.9E[+| -]999
// f format as[-]9.9
// g use e or f format, whichever is the most concise
// G use E or f format, whichever is the most concise
//--------------------------------------------------------------------------------------------------
class DecimalScaleDraw : public QwtScaleDraw
{
public:
virtual QwtText label(double value) const override
{
if (qFuzzyCompare(value + 1.0, 1.0))
value = 0.0;
return QString::number(value, 'f', 3);
}
};
//--------------------------------------------------------------------------------------------------
///
//--------------------------------------------------------------------------------------------------
class ScientificScaleDraw : public QwtScaleDraw
{
public:
virtual QwtText label(double value) const override
{
if (qFuzzyCompare(value + 1.0, 1.0))
value = 0.0;
return QString::number(value, 'e', 3);
}
};
CAF_PDM_SOURCE_INIT(RimSummaryPlot, "SummaryPlot");
@ -106,14 +66,14 @@ RimSummaryPlot::RimSummaryPlot()
m_leftYAxisProperties.uiCapability()->setUiHidden(true);
m_leftYAxisPropertiesObject = std::unique_ptr<RimSummaryYAxisProperties>(new RimSummaryYAxisProperties);
m_leftYAxisPropertiesObject->setName("Left Y-Axis");
m_leftYAxisPropertiesObject->setNameAndAxis("Left Y-Axis", QwtPlot::yLeft);
m_leftYAxisProperties = m_leftYAxisPropertiesObject.get();
CAF_PDM_InitFieldNoDefault(&m_rightYAxisProperties, "RightYAxisProperties", "Right Y Axis", "", "", "");
m_rightYAxisProperties.uiCapability()->setUiHidden(true);
m_rightYAxisPropertiesObject = std::unique_ptr<RimSummaryYAxisProperties>(new RimSummaryYAxisProperties);
m_rightYAxisPropertiesObject->setName("Right Y-Axis");
m_rightYAxisPropertiesObject->setNameAndAxis("Right Y-Axis", QwtPlot::yRight);
m_rightYAxisProperties = m_rightYAxisPropertiesObject.get();
}
@ -150,112 +110,65 @@ void RimSummaryPlot::deletePlotWidget()
//--------------------------------------------------------------------------------------------------
void RimSummaryPlot::updateLeftAndRightYAxis()
{
updateLeftYAxis();
updateRightYAxis();
updateAxis(RimDefines::PLOT_AXIS_LEFT);
updateAxis(RimDefines::PLOT_AXIS_RIGHT);
if (m_qwtPlot) m_qwtPlot->replot();
}
//--------------------------------------------------------------------------------------------------
///
//--------------------------------------------------------------------------------------------------
void RimSummaryPlot::updateLeftYAxis()
void RimSummaryPlot::updateAxis(RimDefines::PlotAxis plotAxis)
{
if (!m_qwtPlot) return;
std::vector<RimSummaryCurve*> curvesForAxis;
std::vector<RimSummaryCurveFilter*> curveFiltersForAxis;
std::vector<RimSummaryCurve*> childCurves;
this->descendantsIncludingThisOfType(childCurves);
for (RimSummaryCurve* curve : childCurves)
{
QString axisTitle = m_leftYAxisPropertiesObject->customTitle;
if (m_leftYAxisPropertiesObject->isAutoTitle) axisTitle = autoAxisTitle();
QwtText axisTitleY = m_qwtPlot->axisTitle(QwtPlot::yLeft);
QFont axisTitleYFont = axisTitleY.font();
axisTitleYFont.setBold(true);
axisTitleYFont.setPixelSize(m_leftYAxisPropertiesObject->fontSize);
axisTitleY.setFont(axisTitleYFont);
axisTitleY.setText(axisTitle);
m_qwtPlot->setAxisTitle(QwtPlot::yLeft, axisTitleY);
}
{
QFont yAxisFont = m_qwtPlot->axisFont(QwtPlot::yLeft);
yAxisFont.setBold(false);
yAxisFont.setPixelSize(m_leftYAxisPropertiesObject->fontSize);
m_qwtPlot->setAxisFont(QwtPlot::yLeft, yAxisFont);
}
{
if (m_leftYAxisPropertiesObject->numberFormat == RimSummaryYAxisProperties::NUMBER_FORMAT_AUTO)
if (curve->associatedPlotAxis() == plotAxis)
{
m_qwtPlot->setAxisScaleDraw(QwtPlot::yLeft, new QwtScaleDraw);
}
else if (m_leftYAxisPropertiesObject->numberFormat == RimSummaryYAxisProperties::NUMBER_FORMAT_DECIMAL)
{
m_qwtPlot->setAxisScaleDraw(QwtPlot::yLeft, new DecimalScaleDraw);
}
else if (m_leftYAxisPropertiesObject->numberFormat == RimSummaryYAxisProperties::NUMBER_FORMAT_SCIENTIFIC)
{
m_qwtPlot->setAxisScaleDraw(QwtPlot::yLeft, new ScientificScaleDraw());
curvesForAxis.push_back(curve);
}
}
for (RimSummaryCurveFilter* cs : m_curveFilters)
{
if (m_leftYAxisPropertiesObject->isLogarithmicScaleEnabled)
if (cs->associatedPlotAxis() == plotAxis)
{
QwtLogScaleEngine* currentScaleEngine = dynamic_cast<QwtLogScaleEngine*>(m_qwtPlot->axisScaleEngine(QwtPlot::yLeft));
if (!currentScaleEngine)
{
m_qwtPlot->setAxisScaleEngine(QwtPlot::yLeft, new QwtLogScaleEngine);
m_qwtPlot->replot();
}
}
else
{
QwtLinearScaleEngine* currentScaleEngine = dynamic_cast<QwtLinearScaleEngine*>(m_qwtPlot->axisScaleEngine(QwtPlot::yLeft));
if (!currentScaleEngine)
{
m_qwtPlot->setAxisScaleEngine(QwtPlot::yLeft, new QwtLinearScaleEngine);
m_qwtPlot->replot();
}
curveFiltersForAxis.push_back(cs);
}
}
}
//--------------------------------------------------------------------------------------------------
///
//--------------------------------------------------------------------------------------------------
void RimSummaryPlot::updateRightYAxis()
{
}
//--------------------------------------------------------------------------------------------------
///
//--------------------------------------------------------------------------------------------------
QString RimSummaryPlot::autoAxisTitle()
{
std::set<std::string> unitNames;
for (RimSummaryCurve* rimCurve : m_curves)
QwtPlot::Axis qwtAxis = QwtPlot::yLeft;
RimSummaryYAxisProperties* yAxisProperties = nullptr;
if (plotAxis == RimDefines::PLOT_AXIS_LEFT)
{
if (rimCurve->isCurveVisible()) unitNames.insert(rimCurve->unitName());
qwtAxis = QwtPlot::yLeft;
yAxisProperties = m_leftYAxisProperties();
}
else
{
qwtAxis = QwtPlot::yRight;
yAxisProperties = m_rightYAxisProperties();
}
for (RimSummaryCurveFilter* curveFilter : m_curveFilters)
if (curvesForAxis.size() > 0)
{
std::set<std::string> filterUnitNames = curveFilter->unitNames();
unitNames.insert(filterUnitNames.begin(), filterUnitNames.end());
m_qwtPlot->enableAxis(qwtAxis, true);
RimSummaryCurvesCalculator calc(yAxisProperties, curvesForAxis, curveFiltersForAxis);
calc.applyPropertiesToPlot(m_qwtPlot);
}
QString assembledYAxisText;
for (const std::string& unitName : unitNames)
else
{
assembledYAxisText += "[" + QString::fromStdString(unitName) + "] ";
m_qwtPlot->enableAxis(qwtAxis, false);
}
return assembledYAxisText;
}
//--------------------------------------------------------------------------------------------------
@ -274,40 +187,6 @@ void RimSummaryPlot::handleViewerDeletion()
updateConnectedEditors();
}
//--------------------------------------------------------------------------------------------------
///
//--------------------------------------------------------------------------------------------------
void RimSummaryPlot::updateYAxisUnit()
{
updateLeftAndRightYAxis();
/*
if (!m_qwtPlot) return;
std::set<std::string> unitNames;
for(RimSummaryCurve* rimCurve: m_curves)
{
if (rimCurve->isCurveVisible()) unitNames.insert(rimCurve->unitName());
}
for(RimSummaryCurveFilter* curveFilter: m_curveFilters)
{
std::set<std::string> filterUnitNames = curveFilter->unitNames();
unitNames.insert(filterUnitNames.begin(), filterUnitNames.end());
}
QString assembledYAxisText;
for (const std::string& unitName : unitNames)
{
assembledYAxisText += "[" + QString::fromStdString(unitName) + "] ";
}
m_qwtPlot->setYAxisTitle(assembledYAxisText);
*/
}
//--------------------------------------------------------------------------------------------------
///
//--------------------------------------------------------------------------------------------------
@ -333,7 +212,6 @@ QWidget* RimSummaryPlot::viewer()
return m_qwtPlot;
}
//--------------------------------------------------------------------------------------------------
///
//--------------------------------------------------------------------------------------------------
@ -374,7 +252,7 @@ void RimSummaryPlot::addCurve(RimSummaryCurve* curve)
if (m_qwtPlot)
{
curve->setParentQwtPlot(m_qwtPlot);
this->updateYAxisUnit();
this->updateLeftAndRightYAxis();
}
}
}
@ -390,7 +268,7 @@ void RimSummaryPlot::addCurveFilter(RimSummaryCurveFilter* curveFilter)
if(m_qwtPlot)
{
curveFilter->setParentQwtPlot(m_qwtPlot);
this->updateYAxisUnit();
this->updateLeftAndRightYAxis();
}
}
}
@ -474,7 +352,7 @@ void RimSummaryPlot::loadDataAndUpdate()
curve->loadDataAndUpdate();
}
this->updateYAxisUnit();
this->updateLeftAndRightYAxis();
updateZoomInQwt();
}

View File

@ -25,6 +25,7 @@
#include "cafAppEnum.h"
#include "cafPdmChildField.h"
#include "RimDefines.h"
#include "RimViewWindow.h"
#include <QPointer>
@ -59,7 +60,6 @@ public:
void loadDataAndUpdate();
void handleViewerDeletion();
void updateYAxisUnit();
void updateCaseNameHasChanged();
QWidget* viewer();
@ -85,9 +85,7 @@ private:
void detachAllCurves();
void deletePlotWidget();
void updateLeftYAxis();
void updateRightYAxis();
QString autoAxisTitle();
void updateAxis(RimDefines::PlotAxis plotAxis);
caf::PdmField<bool> m_showWindow;
caf::PdmField<QString> m_userName;

View File

@ -19,6 +19,7 @@
#include "RimSummaryYAxisProperties.h"
#include "RimSummaryPlot.h"
#include "RimDefines.h"
namespace caf
@ -36,6 +37,31 @@ namespace caf
CAF_PDM_SOURCE_INIT(RimSummaryYAxisProperties, "SummaryYAxisProperties");
//--------------------------------------------------------------------------------------------------
///
//--------------------------------------------------------------------------------------------------
RimSummaryYAxisProperties::RimSummaryYAxisProperties()
{
CAF_PDM_InitObject("Y-Axis Properties", ":/SummaryPlot16x16.png", "", "");
CAF_PDM_InitFieldNoDefault(&m_name, "Name", "Name", "", "", "");
m_name.uiCapability()->setUiHidden(true);
CAF_PDM_InitField(&isAutoTitle, "AutoTitle", true, "Auto Title", "", "", "");
CAF_PDM_InitFieldNoDefault(&customTitle, "CustomTitle", "Title", "", "", "");
CAF_PDM_InitField(&fontSize, "FontSize", 11, "Font Size", "", "", "");
CAF_PDM_InitField(&isAutoScaleEnabled, "AutoScale", true, "Auto Scale", "", "", "");
CAF_PDM_InitField(&visibleRangeMin, "VisibleRangeMin", RimDefines::minimumDefaultValuePlot(), "Min", "", "", "");
CAF_PDM_InitField(&visibleRangeMax, "VisibleRangeMax", RimDefines::maximumDefaultValuePlot(), "Max", "", "", "");
CAF_PDM_InitFieldNoDefault(&numberFormat, "NumberFormat", "Number Format", "", "", "");
CAF_PDM_InitField(&isLogarithmicScaleEnabled, "LogarithmicScale", false, "Logarithmic Scale", "", "", "");
updateOptionSensitivity();
}
//--------------------------------------------------------------------------------------------------
///
//--------------------------------------------------------------------------------------------------
@ -74,34 +100,18 @@ QList<caf::PdmOptionItemInfo> RimSummaryYAxisProperties::calculateValueOptions(c
//--------------------------------------------------------------------------------------------------
///
//--------------------------------------------------------------------------------------------------
RimSummaryYAxisProperties::RimSummaryYAxisProperties()
void RimSummaryYAxisProperties::setNameAndAxis(const QString& name, QwtPlot::Axis axis)
{
CAF_PDM_InitObject("Y-Axis Properties", ":/SummaryPlot16x16.png", "", "");
CAF_PDM_InitFieldNoDefault(&m_name, "Name", "Name", "", "", "");
m_name.uiCapability()->setUiHidden(true);
CAF_PDM_InitField(&isAutoTitle, "AutoTitle", true, "Auto Title", "", "", "");
CAF_PDM_InitFieldNoDefault(&customTitle, "CustomTitle", "Title", "", "", "");
CAF_PDM_InitField(&fontSize, "FontSize", 11, "Font Size", "", "", "");
CAF_PDM_InitField(&isAutoScaleEnabled, "AutoScale", true, "Auto Scale", "", "", "");
CAF_PDM_InitField(&visibleRangeMin, "VisibleRangeMin", m_minLogValueDefault, "Min", "", "", "");
CAF_PDM_InitField(&visibleRangeMax, "VisibleRangeMax", m_maxLogValueDefault, "Max", "", "", "");
CAF_PDM_InitFieldNoDefault(&numberFormat, "NumberFormat", "Number Format", "", "", "");
CAF_PDM_InitField(&isLogarithmicScaleEnabled, "LogarithmicScale", false, "Logarithmic Scale", "", "", "");
updateOptionSensitivity();
m_name = name;
m_axis = axis;
}
//--------------------------------------------------------------------------------------------------
///
//--------------------------------------------------------------------------------------------------
void RimSummaryYAxisProperties::setName(const QString& name)
QwtPlot::Axis RimSummaryYAxisProperties::axis() const
{
m_name = name;
return m_axis;
}
//--------------------------------------------------------------------------------------------------

View File

@ -24,6 +24,8 @@
#include "cafPdmChildArrayField.h"
#include "cafAppEnum.h"
#include "qwt_plot.h"
#include <QString>
//==================================================================================================
@ -42,12 +44,11 @@ public:
NUMBER_FORMAT_SCIENTIFIC
};
public:
RimSummaryYAxisProperties();
void setName(const QString& name);
void setNameAndAxis(const QString& name, QwtPlot::Axis axis);
QwtPlot::Axis axis() const;
caf::PdmField<bool> isAutoTitle;
caf::PdmField<QString> customTitle;
@ -57,7 +58,7 @@ public:
caf::PdmField<double> visibleRangeMin;
caf::PdmField<double> visibleRangeMax;
caf::PdmField< caf::AppEnum< NumberFormatType > > numberFormat;
caf::PdmField< caf::AppEnum< NumberFormatType > > numberFormat;
caf::PdmField<bool> isLogarithmicScaleEnabled;
@ -66,14 +67,12 @@ public:
virtual QList<caf::PdmOptionItemInfo> calculateValueOptions(const caf::PdmFieldHandle* fieldNeedingOptions, bool * useOptionsOnly) override;
protected:
virtual void initAfterRead() override;
virtual void initAfterRead() override;
private:
void updateOptionSensitivity();
private:
caf::PdmField<QString> m_name;
static constexpr double m_minLogValueDefault = - 10.0;
static constexpr double m_maxLogValueDefault = 100.0;
QwtPlot::Axis m_axis;
};