Merge pull request #846 from OpenWaterAnalytics/dev-initsetting

InitSetting added to Link struct
This commit is contained in:
Lew Rossman
2025-04-22 11:22:07 -04:00
committed by GitHub
6 changed files with 95 additions and 72 deletions

View File

@@ -7,7 +7,7 @@
Authors: see AUTHORS
Copyright: see AUTHORS
License: see LICENSE
Last Updated: 02/14/2025
Last Updated: 04/19/2025
******************************************************************************
*/
@@ -3397,7 +3397,7 @@ int DLLEXPORT EN_addlink(EN_Project p, const char *id, int linkType,
link->Type = linkType;
link->N1 = n1;
link->N2 = n2;
link->Status = OPEN;
link->InitStatus = OPEN;
if (linkType == PUMP)
{
@@ -3426,12 +3426,13 @@ int DLLEXPORT EN_addlink(EN_Project p, const char *id, int linkType,
link->Kc = 0.0; // Valve setting.
link->Km = 0.0; // Loss coeff
link->Len = 0.0;
link->Status = ACTIVE;
link->InitStatus = ACTIVE;
}
link->Kb = 0;
link->Kw = 0;
link->LeakArea = 0;
link->LeakExpan = 0;
link->InitSetting = link->Kc;
link->R = 0;
link->Rc = 0;
link->Rpt = 0;
@@ -3685,7 +3686,7 @@ int DLLEXPORT EN_setlinktype(EN_Project p, int *index, int linkType, int actionC
if (oldType <= PIPE && linkType <= PIPE)
{
net->Link[i].Type = linkType;
if (linkType == CVPIPE) net->Link[i].Status = OPEN;
if (linkType == CVPIPE) net->Link[i].InitStatus = OPEN;
return 0;
}
@@ -3788,8 +3789,6 @@ int DLLEXPORT EN_getlinkvalue(EN_Project p, int index, int property, double *val
Slink *Link = net->Link;
Spump *Pump = net->Pump;
double *Ucf = p->Ucf;
double *LinkFlow = hyd->LinkFlow;
double *LinkSetting = hyd->LinkSetting;
// Check for valid arguments
*value = 0.0;
@@ -3827,18 +3826,19 @@ int DLLEXPORT EN_getlinkvalue(EN_Project p, int index, int property, double *val
break;
case EN_INITSTATUS:
if (Link[index].Status <= CLOSED) v = 0.0;
if (Link[index].InitStatus <= CLOSED) v = 0.0;
else v = 1.0;
if (Link[index].Type > PUMP && Link[index].InitStatus > OPEN) v = 2.0;
break;
case EN_INITSETTING:
if (Link[index].Type == PIPE || Link[index].Type == CVPIPE)
{
return EN_getlinkvalue(p, index, EN_ROUGHNESS, value);
}
v = Link[index].Kc;
v = Link[index].InitSetting;
switch (Link[index].Type)
{
case CVPIPE:
case PIPE:
if (hyd->Formflag == DW) v = v * (1000.0 * Ucf[ELEV]);
break;
case PRV:
case PSV:
case PBV:
@@ -3849,9 +3849,6 @@ int DLLEXPORT EN_getlinkvalue(EN_Project p, int index, int property, double *val
default:
break;
}
if (Link[index].Kc == MISSING) {
v = MISSING;
}
break;
case EN_KBULK:
@@ -3864,7 +3861,7 @@ int DLLEXPORT EN_getlinkvalue(EN_Project p, int index, int property, double *val
case EN_FLOW:
if (hyd->LinkStatus[index] <= CLOSED) v = 0.0;
else v = LinkFlow[index] * Ucf[FLOW];
else v = hyd->LinkFlow[index] * Ucf[FLOW];
break;
case EN_VELOCITY:
@@ -3872,7 +3869,7 @@ int DLLEXPORT EN_getlinkvalue(EN_Project p, int index, int property, double *val
else if (hyd->LinkStatus[index] <= CLOSED) v = 0.0;
else
{
q = ABS(LinkFlow[index]);
q = ABS(hyd->LinkFlow[index]);
a = PI * SQR(Link[index].Diam) / 4.0;
v = q / a * Ucf[VELOCITY];
}
@@ -3891,6 +3888,8 @@ int DLLEXPORT EN_getlinkvalue(EN_Project p, int index, int property, double *val
case EN_STATUS:
if (hyd->LinkStatus[index] <= CLOSED) v = 0.0;
else v = 1.0;
if (Link[index].Type > PUMP &&
hyd->LinkStatus[index] > OPEN) v = 2.0;
break;
case EN_SETTING:
@@ -3898,8 +3897,8 @@ int DLLEXPORT EN_getlinkvalue(EN_Project p, int index, int property, double *val
{
return EN_getlinkvalue(p, index, EN_ROUGHNESS, value);
}
if (LinkSetting[index] == MISSING) v = 0.0;
else v = LinkSetting[index];
if (hyd->LinkSetting[index] == MISSING) v = 0.0;
else v = hyd->LinkSetting[index];
switch (Link[index].Type)
{
case PRV:
@@ -4059,7 +4058,6 @@ int DLLEXPORT EN_setlinkvalue(EN_Project p, int index, int property, double valu
Slink *Link = net->Link;
double *Ucf = p->Ucf;
double *LinkSetting = hyd->LinkSetting;
char s;
double r;
int pumpIndex, patIndex, curveIndex;
@@ -4095,7 +4093,8 @@ int DLLEXPORT EN_setlinkvalue(EN_Project p, int index, int property, double valu
if (value <= 0.0) return 211;
Link[index].Kc = value;
if (hyd->Formflag == DW) Link[index].Kc /= (1000.0 * Ucf[ELEV]);
resistcoeff(p, index);
if (p->hydraul.OpenHflag) resistcoeff(p, index);
else Link[index].InitSetting = Link[index].Kc;
}
break;
@@ -4113,14 +4112,15 @@ int DLLEXPORT EN_setlinkvalue(EN_Project p, int index, int property, double valu
// Cannot set status for a check valve
if (Link[index].Type == CVPIPE) return 207;
s = (char)ROUND(value);
if (s < 0 || s > 1) return 211;
if (s < 0 || s > 2) return 211;
s = s + CLOSED;
if (property == EN_INITSTATUS)
{
setlinkstatus(p, index, s, &Link[index].Status, &Link[index].Kc);
Link[index].InitStatus = s;
}
else
{
setlinkstatus(p, index, s, &hyd->LinkStatus[index], &LinkSetting[index]);
setlinkstatus(p, index, s, &hyd->LinkStatus[index], &hyd->LinkSetting[index]);
}
break;
@@ -4128,7 +4128,8 @@ int DLLEXPORT EN_setlinkvalue(EN_Project p, int index, int property, double valu
case EN_SETTING:
if (Link[index].Type == PIPE || Link[index].Type == CVPIPE)
{
return EN_setlinkvalue(p, index, EN_ROUGHNESS, value);
EN_setlinkvalue(p, index, EN_ROUGHNESS, value);
if (property == EN_INITSETTING) Link[index].InitSetting = Link[index].Kc;
}
else
{
@@ -4155,12 +4156,13 @@ int DLLEXPORT EN_setlinkvalue(EN_Project p, int index, int property, double valu
}
if (property == EN_INITSETTING)
{
setlinksetting(p, index, value, &Link[index].Status, &Link[index].Kc);
Link[index].Kc = value;
Link[index].InitSetting = value;
}
else
{
setlinksetting(p, index, value, &hyd->LinkStatus[index],
&LinkSetting[index]);
&hyd->LinkSetting[index]);
}
}
break;
@@ -4253,6 +4255,7 @@ int DLLEXPORT EN_setlinkvalue(EN_Project p, int index, int property, double valu
curveIndex = ROUND(value);
if (curveIndex < 0 || curveIndex > net->Ncurves) return 206;
Link[index].Kc = curveIndex;
if (hyd->OpenHflag == FALSE) Link[index].InitSetting = curveIndex;
}
break;

View File

@@ -1,13 +1,13 @@
/*
******************************************************************************
Project: OWA EPANET
Version: 2.2
Version: 2.3
Module: hydraul.c
Description: implements EPANET's hydraulic engine
Authors: see AUTHORS
Copyright: see AUTHORS
License: see LICENSE
Last Updated: 06/26/2024
Last Updated: 04/19/2025
******************************************************************************
*/
@@ -71,7 +71,7 @@ int openhyd(Project *pr)
if (!errcode) for (i = 1; i <= pr->network.Nlinks; i++)
{
link = &pr->network.Link[i];
initlinkflow(pr, i, link->Status, link->Kc);
initlinkflow(pr, i, link->InitStatus, link->Kc);
}
else closehyd(pr);
return errcode;
@@ -124,8 +124,21 @@ void inithyd(Project *pr, int initflag)
link->ResultIndex = i;
// Initialize status and setting
hyd->LinkStatus[i] = link->Status;
hyd->LinkSetting[i] = link->Kc;
hyd->LinkStatus[i] = link->InitStatus;
hyd->LinkSetting[i] = link->InitSetting;
// Setting of non-ACTIVE FCV, PRV, PSV valves is "MISSING"
switch (link->Type)
{
case FCV:
case PRV:
case PSV:
if (link->InitStatus != ACTIVE)
{
link->Kc = MISSING;
hyd->LinkSetting[i] = MISSING;
}
}
// Compute flow resistance
resistcoeff(pr, i);

View File

@@ -7,7 +7,7 @@ Description: saves network data to an EPANET formatted text file
Authors: see AUTHORS
Copyright: see AUTHORS
License: see LICENSE
Last Updated: 03/11/2025
Last Updated: 04/19/2025
******************************************************************************
*/
@@ -210,7 +210,7 @@ int saveinpfile(Project *pr, const char *fname)
if (link->Type <= PIPE)
{
d = link->Diam;
kc = link->Kc;
kc = link->InitSetting;
if (hyd->Formflag == DW) kc = kc * pr->Ucf[ELEV] * 1000.0;
km = link->Km * SQR(d) * SQR(d) / 0.02517;
@@ -219,7 +219,7 @@ int saveinpfile(Project *pr, const char *fname)
link->Len * pr->Ucf[LENGTH], d * pr->Ucf[DIAM], kc, km);
if (link->Type == CVPIPE) sprintf(s2, "CV");
else if (link->Status == CLOSED) sprintf(s2, "CLOSED");
else if (link->InitStatus == CLOSED) sprintf(s2, "CLOSED");
else strcpy(s2, " ");
fprintf(f, "\n%s\t%-6s", s, s2);
if (link->Comment) fprintf(f, "\t;%s", link->Comment);
@@ -267,9 +267,9 @@ int saveinpfile(Project *pr, const char *fname)
}
// Optional speed setting
if (link->Kc != 1.0)
if (link->InitSetting != 1.0)
{
sprintf(s1, "\tSPEED %.4f", link->Kc);
sprintf(s1, "\tSPEED %.4f", link->InitSetting);
strcat(s, s1);
}
@@ -289,8 +289,7 @@ int saveinpfile(Project *pr, const char *fname)
d = link->Diam;
// Valve setting
kc = link->Kc;
if (kc == MISSING) kc = 0.0;
kc = link->InitSetting;
switch (link->Type)
{
case FCV:
@@ -312,7 +311,7 @@ int saveinpfile(Project *pr, const char *fname)
LinkTxt[link->Type]);
// For GPV, setting = head curve index
if (link->Type == GPV && (j = ROUND(link->Kc)) > 0)
if (link->Type == GPV && (j = ROUND(kc)) > 0)
{
sprintf(s1, "%-31s\t%-12.4f", net->Curve[j].ID, km);
}
@@ -384,7 +383,7 @@ int saveinpfile(Project *pr, const char *fname)
link = &net->Link[i];
if (link->Type <= PUMP)
{
if (link->Status == CLOSED)
if (link->InitStatus == CLOSED)
{
fprintf(f, "\n %-31s\t%s", link->ID, StatTxt[CLOSED]);
}
@@ -395,21 +394,21 @@ int saveinpfile(Project *pr, const char *fname)
n = findpump(net, i);
pump = &net->Pump[n];
if (pump->Hcurve == 0 && pump->Ptype != CONST_HP &&
link->Kc != 1.0)
link->InitSetting != 1.0)
{
fprintf(f, "\n %-31s\t%-.4f", link->ID, link->Kc);
fprintf(f, "\n %-31s\t%-.4f", link->ID, link->InitSetting);
}
}
}
// Write fixed-status PRVs & PSVs (setting = MISSING)
else if (link->Kc == MISSING)
// Write fixed-status valves
else
{
if (link->Status == OPEN)
if (link->InitStatus == OPEN)
{
fprintf(f, "\n %-31s\t%s", link->ID, StatTxt[OPEN]);
}
if (link->Status == CLOSED)
if (link->InitStatus == CLOSED)
{
fprintf(f, "\n%-31s\t%s", link->ID, StatTxt[CLOSED]);
}

View File

@@ -1,13 +1,13 @@
/*
******************************************************************************
Project: OWA EPANET
Version: 2.2
Version: 2.3
Module: input1.c
Description: retrieves network data from an EPANET input file
Authors: see AUTHORS
Copyright: see AUTHORS
License: see LICENSE
Last Updated: 06/15/2024
Last Updated: 04/19/2025
******************************************************************************
*/
@@ -624,6 +624,7 @@ void convertunits(Project *pr)
break;
}
}
link->InitSetting = link->Kc;
}
// Convert units on control settings

View File

@@ -7,7 +7,7 @@ Description: parses network data from a line of an EPANET input file
Authors: see AUTHORS
Copyright: see AUTHORS
License: see LICENSE
Last Updated: 03/10/2025
Last Updated: 04/19/2025
******************************************************************************
*/
@@ -391,7 +391,8 @@ int pipedata(Project *pr)
link->LeakArea = 0.0;
link->LeakExpan = 0.0;
link->Type = PIPE;
link->Status = OPEN;
link->InitStatus = OPEN;
link->InitSetting = link->Kc;
link->Rpt = 0;
link->ResultIndex = 0;
link->Comment = xstrcpy(&link->Comment, parser->Comment, MAXMSG);
@@ -420,8 +421,8 @@ int pipedata(Project *pr)
if (n > 6)
{
if (match(parser->Tok[6], w_CV)) link->Type = CVPIPE;
else if (match(parser->Tok[6], w_CLOSED)) link->Status = CLOSED;
else if (match(parser->Tok[6], w_OPEN)) link->Status = OPEN;
else if (match(parser->Tok[6], w_CLOSED)) link->InitStatus = CLOSED;
else if (match(parser->Tok[6], w_OPEN)) link->InitStatus = OPEN;
else
{
if (!getfloat(parser->Tok[6], &x) || x < 0.0)
@@ -437,8 +438,8 @@ int pipedata(Project *pr)
return setError(parser, 6, 202);
link->Km = x;
if (match(parser->Tok[7], w_CV)) link->Type = CVPIPE;
else if (match(parser->Tok[7], w_CLOSED)) link->Status = CLOSED;
else if (match(parser->Tok[7], w_OPEN)) link->Status = OPEN;
else if (match(parser->Tok[7], w_CLOSED)) link->InitStatus = CLOSED;
else if (match(parser->Tok[7], w_OPEN)) link->InitStatus = OPEN;
else return setError(parser, 7, 213);
}
return 0;
@@ -500,7 +501,8 @@ int pumpdata(Project *pr)
link->LeakArea = 0.0;
link->LeakExpan = 0.0;
link->Type = PUMP;
link->Status = OPEN;
link->InitStatus = OPEN;
link->InitSetting = 1.0;
link->Rpt = 0;
link->ResultIndex = 0;
link->Comment = xstrcpy(&link->Comment, parser->Comment, MAXMSG);
@@ -545,6 +547,7 @@ int pumpdata(Project *pr)
else return setError(parser, m-1, 201);;
m = m + 2; // Move to next keyword token
}
link->InitSetting = link->Kc;
return 0;
}
@@ -621,7 +624,8 @@ int valvedata(Project *pr)
link->LeakArea = 0.0;
link->LeakExpan = 0.0;
link->Type = type;
link->Status = ACTIVE;
link->InitStatus = ACTIVE;
link->InitSetting = 0.0;
link->Rpt = 0;
link->ResultIndex = 0;
link->Comment = xstrcpy(&link->Comment, parser->Comment, MAXMSG);
@@ -641,7 +645,7 @@ int valvedata(Project *pr)
if (c == 0) return setError(parser, 5, 206);
link->Kc = c;
net->Curve[c].Type = HLOSS_CURVE;
link->Status = OPEN;
link->InitStatus = OPEN;
}
else
{
@@ -664,6 +668,7 @@ int valvedata(Project *pr)
net->Curve[c].Type = VALVE_CURVE;
if (link->Kc > 100.0) link->Kc = 100.0;
}
link->InitSetting = link->Kc;
return 0;
}
@@ -2213,6 +2218,7 @@ int tagdata(Project *pr)
}
return 0;
}
void changestatus(Network *net, int j, StatusType status, double y)
/*
**--------------------------------------------------------------
@@ -2221,11 +2227,10 @@ void changestatus(Network *net, int j, StatusType status, double y)
** y = numerical setting (pump speed, valve
** setting)
** Output: none
** Purpose: changes status or setting of a link
** Purpose: changes initial status or setting of a link
**
** NOTE: If status = ACTIVE, then a numerical setting (y) was
** supplied. If status = OPEN/CLOSED, then numerical
** setting is 0.
** supplied.
**--------------------------------------------------------------
*/
{
@@ -2233,7 +2238,7 @@ void changestatus(Network *net, int j, StatusType status, double y)
if (link->Type == PIPE || link->Type == GPV)
{
if (status != ACTIVE) link->Status = status;
if (status != ACTIVE) link->InitStatus = status;
}
else if (link->Type == PUMP)
{
@@ -2245,12 +2250,13 @@ void changestatus(Network *net, int j, StatusType status, double y)
}
else if (status == OPEN) link->Kc = 1.0;
else if (status == CLOSED) link->Kc = 0.0;
link->Status = status;
link->InitStatus = status;
link->InitSetting = link->Kc;
}
else if (link->Type >= PRV)
{
link->Kc = y;
link->Status = status;
if (status != ACTIVE) link->Kc = MISSING;
if (status == ACTIVE) link->Kc = y;
link->InitStatus = status;
link->InitSetting = link->Kc;
}
}

View File

@@ -7,7 +7,7 @@
Authors: see AUTHORS
Copyright: see AUTHORS
License: see LICENSE
Last Updated: 02/14/2025
Last Updated: 04/19/2025
******************************************************************************
*/
@@ -408,7 +408,7 @@ typedef struct // Link Object
int N2; // end node index
double Diam; // diameter
double Len; // length
double Kc; // roughness
double Kc; // pipe roughness, pump speed, valve setting
double Km; // minor loss coeff.
double Kb; // bulk react. coeff.
double Kw; // wall react. coef.
@@ -417,7 +417,8 @@ typedef struct // Link Object
double LeakArea; // leak area (sq mm per 100 pipe length units
double LeakExpan; // leak expansion (sq mm per unit of head)
LinkType Type; // link type
StatusType Status; // initial status
StatusType InitStatus; // initial status
double InitSetting; // initial setting
Pvertices Vertices; // internal vertex coordinates
int Rpt; // reporting flag
int ResultIndex; // saved result index