diff --git a/Bin/Config/Lang/cn/nmNum_cn.qm b/Bin/Config/Lang/cn/nmNum_cn.qm
index 9114077..30a8be1 100644
Binary files a/Bin/Config/Lang/cn/nmNum_cn.qm and b/Bin/Config/Lang/cn/nmNum_cn.qm differ
diff --git a/Bin/Config/Lang/cn/nmNum_cn.ts b/Bin/Config/Lang/cn/nmNum_cn.ts
index 47360c0..cb8b179 100644
--- a/Bin/Config/Lang/cn/nmNum_cn.ts
+++ b/Bin/Config/Lang/cn/nmNum_cn.ts
@@ -7284,6 +7284,7 @@ Average pressure in contour: %2 MPa
nmReservoirParameterPage
Object display对象显示
Display:显示:
+ Storage calculator井储计算器
No editable objects in this category.此分类中没有可编辑对象。
Initial oil and water saturations must sum to 1.初始含油饱和度与初始含水饱和度之和必须为 1。
diff --git a/Include/nmNum/nmSubWxs/nmReservoirParameterPage.h b/Include/nmNum/nmSubWxs/nmReservoirParameterPage.h
index d8d7d12..abcb442 100644
--- a/Include/nmNum/nmSubWxs/nmReservoirParameterPage.h
+++ b/Include/nmNum/nmSubWxs/nmReservoirParameterPage.h
@@ -75,6 +75,9 @@ private slots:
/** @brief 枚举code变化后保存并执行集中联动。 */
void slotEnumIndexChanged(int nIndex);
+ /** @brief 计算并回填当前井的井筒储集系数。 */
+ void slotWellboreStorageCalculator();
+
private:
/** @brief 创建对象显示控制区和单层参数分组区域。 */
void createUi();
diff --git a/Src/nmNum/nmSubWxs/nmReservoirParameterPage.cpp b/Src/nmNum/nmSubWxs/nmReservoirParameterPage.cpp
index 43158c0..5d4e7ad 100644
--- a/Src/nmNum/nmSubWxs/nmReservoirParameterPage.cpp
+++ b/Src/nmNum/nmSubWxs/nmReservoirParameterPage.cpp
@@ -2,13 +2,18 @@
#include "nmParameterField.h"
#include "nmReservoirPropertiesSession.h"
+#include "nmWxWellboreStorageCalculator.h"
#include
+#include
+#include
#include
#include
#include
+#include
#include
#include
+#include
#include
#include
@@ -261,6 +266,57 @@ bool nmReservoirParameterPage::buildGroup(
nFieldColumnOffset + 2,
nmParameterField::unitMinimumWidth());
+ bool bHasWellboreStorage = false;
+ for (int nFieldIndex = 0;
+ nFieldIndex < oGroupInfo.m_listFields.size();
+ ++nFieldIndex)
+ {
+ if (oGroupInfo.m_listFields[nFieldIndex].m_sBaseParameterId ==
+ "W_C")
+ {
+ bHasWellboreStorage = true;
+ break;
+ }
+ }
+
+ int nFirstFieldRow = 0;
+ if (m_eCategory == NM_RESERVOIR_PAGE_WELL &&
+ bHasWellboreStorage)
+ {
+ // 计算器单独占用分组首行,标签和按钮分别对齐
+ // 下方参数的名称列右边界和数值列左边界。
+ QLabel* pCalculatorLabel = new QLabel(
+ tr("Storage calculator"), pGroupBox);
+ pCalculatorLabel->setAlignment(
+ Qt::AlignRight | Qt::AlignVCenter);
+ pCalculatorLabel->setWordWrap(false);
+ QToolButton* pCalculatorButton =
+ new QToolButton(pGroupBox);
+ QString sIconDir = QCoreApplication::applicationDirPath()
+ .section('/', 0, -2) + "/Res/Icon/";
+ pCalculatorButton->setIcon(QIcon(
+ sIconDir + "NmWellboreStorageCalculator.png"));
+ pCalculatorButton->setIconSize(QSize(20, 20));
+ pCalculatorButton->setFixedSize(26, 26);
+ pCalculatorButton->setAutoRaise(true);
+ pCalculatorButton->setToolTip(
+ tr("Storage calculator"));
+ connect(pCalculatorButton, SIGNAL(clicked()),
+ this, SLOT(slotWellboreStorageCalculator()));
+
+ pFieldLayout->addWidget(
+ pCalculatorLabel,
+ 0,
+ nFieldColumnOffset,
+ Qt::AlignRight | Qt::AlignVCenter);
+ pFieldLayout->addWidget(
+ pCalculatorButton,
+ 0,
+ nFieldColumnOffset + 1,
+ Qt::AlignLeft | Qt::AlignVCenter);
+ nFirstFieldRow = 1;
+ }
+
// 每个字段只把三个直接控件放入此网格,不产生字段外框或子面板。
for (int nFieldIndex = 0;
nFieldIndex < oGroupInfo.m_listFields.size();
@@ -272,7 +328,7 @@ bool nmReservoirParameterPage::buildGroup(
m_pUnitService,
pGroupBox);
if (!pField->initialize(pFieldLayout,
- nFieldIndex,
+ nFirstFieldRow + nFieldIndex,
nFieldColumnOffset,
sError))
{
@@ -481,6 +537,43 @@ void nmReservoirParameterPage::slotEnumIndexChanged(int nIndex)
updateValidity();
}
+void nmReservoirParameterPage::slotWellboreStorageCalculator()
+{
+ if (m_nCurrentObjectIndex < 0 ||
+ m_nCurrentObjectIndex >= m_listObjectInfos.size())
+ {
+ return;
+ }
+
+ // 只定位当前井的W_C字段,不访问实时井或全局当前井。
+ const nmReservoirPropertyObjectInfo& oObjectInfo =
+ m_listObjectInfos[m_nCurrentObjectIndex];
+ nmParameterField* pWellboreStorageField =
+ m_mapFields.value(
+ oObjectInfo.m_sObjectCode + "_W_C", nullptr);
+ if (pWellboreStorageField == nullptr)
+ {
+ return;
+ }
+
+ nmWxWellboreStorageCalculator oCalculator(this);
+ if (oCalculator.exec() != QDialog::Accepted)
+ {
+ return;
+ }
+
+ double dWellboreStorage =
+ oCalculator.getWellboreStorageValue();
+ if (dWellboreStorage < 0.0)
+ {
+ return;
+ }
+
+ // 仅回填页面字段;切换井或外层确定时才写入会话工作副本。
+ pWellboreStorageField->setBaseValue(dWellboreStorage);
+ updateValidity();
+}
+
void nmReservoirParameterPage::applyVisibilityRules()
{
if (m_pSession == nullptr || m_nCurrentObjectIndex < 0 ||