#2054 Curve Calc. Add context menu with operators and functions

This commit is contained in:
Bjørn Erik Jensen
2017-11-02 15:29:39 +01:00
parent 9b7cfdd913
commit 0f6d5f9c48
7 changed files with 237 additions and 6 deletions

View File

@@ -256,3 +256,14 @@ void RicSummaryCurveCalculator::defineEditorAttribute(const caf::PdmFieldHandle*
RicSummaryCurveCalculator::assignPushButtonEditorText(attribute, "Delete Calculation");
}
}
//--------------------------------------------------------------------------------------------------
///
//--------------------------------------------------------------------------------------------------
void RicSummaryCurveCalculator::onEditorWidgetsCreated()
{
if (m_currentCalculation() != nullptr)
{
m_currentCalculation->attachToWidget();
}
}

View File

@@ -49,6 +49,7 @@ private:
virtual void defineUiOrdering(QString uiConfigName, caf::PdmUiOrdering& uiOrdering) override;
virtual QList<caf::PdmOptionItemInfo> calculateValueOptions(const caf::PdmFieldHandle* fieldNeedingOptions, bool* useOptionsOnly) override;
virtual void defineEditorAttribute(const caf::PdmFieldHandle* field, QString uiConfigName, caf::PdmUiEditorAttribute* attribute) override;
virtual void onEditorWidgetsCreated();
private:
static RimSummaryCalculationCollection* calculationCollection();

View File

@@ -30,11 +30,14 @@
#include "RimSummaryPlot.h"
#include "RimSummaryPlotCollection.h"
#include "RiuExpressionContextMenuManager.h"
#include "cafPdmUiTextEditor.h"
#include <QMessageBox>
#include <algorithm>
#include "QMenu"
CAF_PDM_SOURCE_INIT(RimSummaryCalculation, "RimSummaryCalculation");
@@ -56,6 +59,8 @@ RimSummaryCalculation::RimSummaryCalculation()
CAF_PDM_InitFieldNoDefault(&m_calculatedValues, "CalculatedValues", "Calculated Values", "", "", "");
CAF_PDM_InitFieldNoDefault(&m_timesteps, "TimeSteps", "Time Steps", "", "", "");
m_exprContextMenuMgr = std::unique_ptr<RiuExpressionContextMenuManager>(new RiuExpressionContextMenuManager());
}
//--------------------------------------------------------------------------------------------------
@@ -300,6 +305,30 @@ QString RimSummaryCalculation::findLeftHandSide(const QString& expresion)
return "";
}
//--------------------------------------------------------------------------------------------------
///
//--------------------------------------------------------------------------------------------------
void RimSummaryCalculation::attachToWidget()
{
for (auto e : m_expression.uiCapability()->connectedEditors())
{
caf::PdmUiTextEditor* textEditor = dynamic_cast<caf::PdmUiTextEditor*>(e);
if (!textEditor) continue;
QWidget* containerWidget = textEditor->editorWidget();
if (!containerWidget) continue;
for (auto qObj : containerWidget->children())
{
QTextEdit* textEdit = dynamic_cast<QTextEdit*>(qObj);
if (textEdit)
{
m_exprContextMenuMgr->attachTextEdit(textEdit);
}
}
}
}
//--------------------------------------------------------------------------------------------------
///
//--------------------------------------------------------------------------------------------------

View File

@@ -18,11 +18,15 @@
#pragma once
#include "RiuExpressionContextMenuManager.h"
#include "cafPdmChildArrayField.h"
#include "cafPdmObject.h"
#include "cafPdmField.h"
#include <QPointer>
#include <memory>
class RimSummaryCalculationVariable;
class QTextEdit;
//==================================================================================================
///
@@ -50,6 +54,7 @@ public:
virtual caf::PdmFieldHandle* userDescriptionField() override;
static QString findLeftHandSide(const QString& expresion);
void attachToWidget();
private:
RimSummaryCalculationVariable* findByName(const QString& name) const;
@@ -66,4 +71,6 @@ private:
caf::PdmField<std::vector<double>> m_calculatedValues;
caf::PdmField<std::vector<time_t>> m_timesteps;
std::unique_ptr<RiuExpressionContextMenuManager> m_exprContextMenuMgr;
};

View File

@@ -60,6 +60,7 @@ ${CEE_CURRENT_LIST_DIR}RiuSummaryCurveDefSelection.h
${CEE_CURRENT_LIST_DIR}RiuSummaryCurveDefSelectionDialog.h
${CEE_CURRENT_LIST_DIR}RiuSummaryCurveDefSelectionEditor.h
${CEE_CURRENT_LIST_DIR}RiuSummaryVectorDescriptionMap.h
${CEE_CURRENT_LIST_DIR}RiuExpressionContextMenuManager.h
)
set (SOURCE_GROUP_SOURCE_FILES
@@ -116,6 +117,7 @@ ${CEE_CURRENT_LIST_DIR}RiuSummaryCurveDefSelection.cpp
${CEE_CURRENT_LIST_DIR}RiuSummaryCurveDefSelectionDialog.cpp
${CEE_CURRENT_LIST_DIR}RiuSummaryCurveDefSelectionEditor.cpp
${CEE_CURRENT_LIST_DIR}RiuSummaryVectorDescriptionMap.cpp
${CEE_CURRENT_LIST_DIR}RiuExpressionContextMenuManager.cpp
)
list(APPEND CODE_HEADER_FILES
@@ -152,6 +154,7 @@ ${CEE_CURRENT_LIST_DIR}RiuWellPltPlot.h
${CEE_CURRENT_LIST_DIR}RiuFlowCharacteristicsPlot.h
${CEE_CURRENT_LIST_DIR}RiuNightchartsWidget.h
${CEE_CURRENT_LIST_DIR}RiuMessagePanel.h
${CEE_CURRENT_LIST_DIR}RiuExpressionContextMenuManager.h
)
list(APPEND QT_UI_FILES

View File

@@ -0,0 +1,124 @@
/////////////////////////////////////////////////////////////////////////////////
//
// Copyright (C) 2017 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 "RiuExpressionContextMenuManager.h"
#include <QTextEdit>
#include <QMenu>
const std::map<QString, std::set<QString>> RiuExpressionContextMenuManager::MENU_MAP =
{
{
"Basic Operators",
{
"+", "-", "*", "/", "%", "^"
}
},
{
"Assignment Operators",
{
":=", "+=", "-=", "*=", "/=", "%="
}
},
{
"Functions",
{
"abs(x)", "avg(x, y, ...)", "ceil(x)", "clamp(r0, x, r1)",
"floor(x)", "frac(x)", "log(x)", "log10(x)",
"max(x, y, ...)", "min(x, y, ...)", "pow(x, y)", "root(x, y)",
"round(x)", "roundn(x, d)", "sgn(x)", "sqrt(x)", "sum(x, y, ...)",
"trunc(x)"
}
},
{
"Trigonometry Functions",
{
"acos(x)", "acosh(x)", "asin(x)", "asinh(x)", "atan(x)", "atanh(x)",
"cos(x)", "cosh(x)", "cot(x)", "csc(x)", "sec(x)", "sin(x)", "sinc(x)", "sinh(x)",
"tan(x)", "tanh(x)", "rad2deg(x)", "deg2grad(x)", "deg2rad(x)", "grad2deg(x)"
}
}
};
//--------------------------------------------------------------------------------------------------
///
//--------------------------------------------------------------------------------------------------
void RiuExpressionContextMenuManager::attachTextEdit(QTextEdit* textEdit)
{
if (m_textEdit != textEdit)
{
textEdit->setContextMenuPolicy(Qt::CustomContextMenu);
QObject::connect(textEdit, SIGNAL(customContextMenuRequested(QPoint)), this, SLOT(slotMenuItems(QPoint)));
}
m_textEdit = textEdit;
}
//--------------------------------------------------------------------------------------------------
///
//--------------------------------------------------------------------------------------------------
void RiuExpressionContextMenuManager::slotMenuItems(QPoint point)
{
QMenu menu;
for (const std::pair<QString, std::set<QString>>& subMenuPair : MENU_MAP)
{
QMenu* subMenu = menu.addMenu(subMenuPair.first);
for (const QString& menuItemText : subMenuPair.second)
{
if (m_actionCache.count(menuItemText) == 0)
{
QAction* action = new QAction(menuItemText, this);
connect(action, SIGNAL(triggered()), SLOT(slotShowText()));
m_actionCache.insert(std::make_pair(menuItemText, std::unique_ptr<QAction>(action)));
}
subMenu->addAction(m_actionCache[menuItemText].get());
}
}
QPoint globalPoint = point;
if (m_textEdit)
{
globalPoint = m_textEdit->mapToGlobal(point);
m_textPosition = m_textEdit->textCursor().position();
}
menu.exec(globalPoint);
}
//--------------------------------------------------------------------------------------------------
///
//--------------------------------------------------------------------------------------------------
void RiuExpressionContextMenuManager::slotShowText()
{
if (m_textEdit)
{
QAction* action = qobject_cast<QAction *>(sender());
if (action)
{
QTextCursor cursor = m_textEdit->textCursor();
cursor.setPosition(m_textPosition);
m_textEdit->setTextCursor(cursor);
m_textEdit->insertPlainText(action->text());
}
}
}

View File

@@ -0,0 +1,56 @@
/////////////////////////////////////////////////////////////////////////////////
//
// Copyright (C) 2017 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 "cafPdmChildArrayField.h"
#include "cafPdmObject.h"
#include "cafPdmField.h"
#include <QPointer>
#include <QAction>
#include <memory>
class RimSummaryCalculationVariable;
class QTextEdit;
//==================================================================================================
///
///
//==================================================================================================
class RiuExpressionContextMenuManager : public QObject
{
Q_OBJECT
static const std::map<QString, std::set<QString>> MENU_MAP;
public:
RiuExpressionContextMenuManager() { }
void attachTextEdit(QTextEdit* textEdit);
public slots:
void slotMenuItems(QPoint point);
private slots:
void slotShowText();
private:
QPointer<QTextEdit> m_textEdit;
int m_textPosition;
std::map<QString, std::unique_ptr<QAction>> m_actionCache;
};