Thursday, February 2, 2023

ChatGPT Version of the SWMM5 Wikipedia Page Introduction

 The EPA Storm Water Management Model (SWMM) is a computer software that simulates the rainfall-runoff-routing process in urban areas. It operates by dividing the study area into smaller subcatchment areas, where the hydrologic processes producing runoff are accounted for, including time-varying rainfall, evaporation, snow accumulation, depression storage, and more. The runoff is then routed through a network of pipes, channels, storage/treatment units, pumps, and regulators using hydraulic modeling techniques. The model can handle networks of any size, model different flow regimes, and use either kinematic wave or dynamic wave flow routing methods.

SWMM has been widely used in various applications, such as flood control, waste load allocation studies, and master planning of sewer collection systems. It is public domain software that can be freely copied and distributed, with the C engine code and Delphi graphical user interface code easily edited for custom features.

Applications:

  • Design and sizing of drainage system components for flood control
  • Sizing of detention facilities for flood control and water quality protection
  • Flood plain mapping of natural channel systems
  • Minimizing Combined Sewer Overflow (CSO) and Sanitary Sewer Overflow (SSO)
  • Evaluating the impact of inflow and infiltration on sanitary sewer overflows
  • Generating non-point source pollutant loadings for waste load allocation studies
  • Evaluating the effectiveness of Best Management Practices (BMPs) and Low Impact Development (LID) practices
  • Rainfall-runoff modeling of urban and rural watersheds
  • Hydraulic and water quality analysis of storm, sanitary, and combined sewer systems
  • Master planning of sewer collection systems and urban watersheds
  • System evaluations associated with EPA regulations, such as NPDES permits, CMOM, and TMDL
  • 1D and 2D predictions of flood levels and flooding volume

Hydrologic Processes Accounted for in SWMM:

  • Time-varying rainfall
  • Evaporation of standing surface water
  • Snow accumulation and melting
  • Rainfall interception from depression storage
  • Infiltration of rainfall into unsaturated soil layers
  • Percolation of infiltrated water into groundwater layers
  • Interflow between groundwater and the drainage system
  • Nonlinear reservoir routing of overland flow
  • Capture and retention of rainfall/runoff by LID practices

Hydraulic Modeling Capabilities:

  • Handle networks of unlimited size
  • Use a variety of standard closed and open conduit shapes and natural channels
  • Model special elements such as storage/treatment units, flow dividers, pumps, weirs, and orifices
  • Apply external flows and water quality inputs from various sources
  • Use either kinematic wave or full dynamic wave flow routing methods
  • Model various flow regimes, such as backwater, surcharging, reverse flow, and surface ponding
  • Apply user-defined dynamic control rules to simulate the operation of pumps, orifice openings, and weir crest levels.

Friday, January 27, 2023

XPSWMM to ICM SWMM or ICM Process Pathways

 


#ProcessDescription
1Technical details about how XPSWMM models a featureThis process involves understanding the specific algorithms, equations, and data inputs used by XPSWMM to model different features of an urban drainage system, such as hydrology, hydraulics, and water quality. This includes understanding how XPSWMM calculates runoff, infiltration, evaporation, and other hydrologic processes, as well as how it models the flow and routing of water through the drainage system.
2The process of exporting a XPSWMM model to XPXThis process involves using the export functionality in XPSWMM to save the model in a format that can be used in the XPX software. This includes selecting the components of the model to export, specifying the export location, and ensuring that the exported file is in a format that can be read by XPX.
3The process of exporting a XPSWMM model to SWMM5This process involves using the export functionality in XPSWMM to save the model in a format that can be used in the SWMM5 software. This includes selecting the components of the model to export, specifying the export location, and ensuring that the exported file is in a format that can be read by SWMM5.
4The process of importing the SWMM5 model to ICM SWMMThis process involves using the import functionality in ICM SWMM to load the model exported from SWMM5. This includes specifying the location of the exported file, mapping the components of the model to the appropriate inputs in ICM SWMM, and checking for any errors or inconsistencies in the imported model.
5The process of importing the SWMM5 model to ICMThis process involves using the import functionality in ICM to load the model exported from SWMM5. This includes specifying the location of the exported file, mapping the components of the model to the appropriate inputs in ICM, and checking for any errors or inconsistencies in the imported model.
6Validating the ICM SWMM ImportThis process involves checking the imported model in ICM SWMM for errors or inconsistencies. This includes comparing the imported data to the original XPSWMM model, checking for missing or incorrect data, and making any necessary adjustments to the imported model before running the simulation.
7Converting the ICM SWMM network to ICMThis process involves converting the imported model in ICM SWMM to the format used by the ICM software. This includes mapping the components of the model to the appropriate inputs in ICM, and making any necessary adjustments to the imported model before running the simulation.
8Getting either ICM or ICM SWMM to runThis process involves configuring the software and the model, and then running the simulation. This includes setting the simulation parameters, specifying the time step and duration of the simulation, and specifying the output options.
9Compare answers to XPSWMMThis process involves comparing the results of the XPSWMM simulation to the results of the simulation run in ICM or ICM SWMM. This includes comparing the hydrographs, water surface elevations, and other output variables, and identifying any discrepancies or issues with the results.
10Technical details on how SWMM5 or ICM work compared to XPSWMMThis process involves identifying and implementing solutions to issues or problems that may arise during the use of the software or the simulation.

Sunday, January 22, 2023

SWMM 5.2.2 LID code for readSurfaceData

This code reads data for a specific LID process from a line of an input file, and assigns the data to variables in an array called "LidProcs". The data includes values for storage height, vegetation volume fraction, roughness, surface slope, and side slope. The code first checks if there are enough tokens in the input file, and then uses a loop to check if each token is a valid number and is greater than or equal to 0. If any of these conditions are not met, an error code is returned. The code then assigns the data to the appropriate variables in the LidProcs array, after converting the units and making sure that some values are set to 0 if other values meet certain conditions. The code returns 0 if there is no error.

int readSurfaceData(int j, char* toks[], int ntoks)
//
//  Purpose: reads surface layer data for a LID process from line of input
//           data file
//  Input:   j = LID process index 
//           toks = array of string tokens
//           ntoks = number of tokens
//  Output:  returns error code
//
//  Format of data is:
//  LID_ID  SURFACE  StorageHt  VegVolFrac  Roughness  SurfSlope  SideSlope
//
{
    int    i;
    double x[5];

    if ( ntoks < 7 ) return error_setInpError(ERR_ITEMS, "");
    for (i = 2; i < 7; i++)
    {
        if ( ! getDouble(toks[i], &x[i-2]) || x[i-2] < 0.0 )
            return error_setInpError(ERR_NUMBER, toks[i]);
    }
    if ( x[1] >= 1.0 ) return error_setInpError(ERR_NUMBER, toks[3]);           
    if ( x[0] == 0.0 ) x[1] = 0.0;

    LidProcs[j].surface.thickness     = x[0] / UCF(RAINDEPTH);
    LidProcs[j].surface.voidFrac      = 1.0 - x[1];
    LidProcs[j].surface.roughness     = x[2];
    LidProcs[j].surface.surfSlope     = x[3] / 100.0;
    LidProcs[j].surface.sideSlope     = x[4];
    return 0;
}

Saturday, January 21, 2023

SWMM 5.2.2 Code for LID Function lidproc_getOutflow

 This code is part of a function called "lidproc_getOutflow" that computes the runoff outflow from a single LID (Low Impact Development) unit.

The function takes in multiple inputs: a pointer to a specific LID unit, a pointer to a generic LID process, the runoff rate captured by the LID unit, potential evaporation rate, infiltration rate to native soil, maximum infiltration rate to native soil, and time step. It returns surface runoff rate from the LID unit, and sets the values of lidEvap, lidInfil, and lidDrain.

The function uses several arrays and variables to store values such as layer moisture levels, previously and newly computed flux rates, and layer moisture limits. It also defines a pointer to a function that computes flux rates through the LID. It initializes various values such as layer moisture volumes, flux rates, and moisture limits. Then it finds Green-Ampt infiltration from the surface layer and calls the appropriate flux rate function for the LID type.

Input VariablesTypeDescriptionUnits
lidUnitpointerPointer to specific LID unit being analyzed
lidProcpointerPointer to generic LID process of the LID unit
inflowdoubleRunoff rate captured by LID unitft/s
evapdoublePotential evaporation rateft/s
infildoubleInfiltration rate to native soilft/s
maxInfildoubleMaximum infiltration rate to native soilft/s
tStepdoubleTime stepsec
Output VariablesTypeDescriptionUnits
lidEvapdouble pointerEvaporation rate for LID unitft/s
lidInfildouble pointerInfiltration rate for LID unitft/s
lidDraindouble pointerDrain flow for LID unitft/s
returnsdoubleSurface runoff rate from the LID unitft/s

Note: The table only contains the input/output variables defined in the function signature and the purpose of the function.

double lidproc_getOutflow(TLidUnit* lidUnit, TLidProc* lidProc, double inflow,
                          double evap, double infil, double maxInfil,
                          double tStep, double* lidEvap,
                          double* lidInfil, double* lidDrain)
//
//  Purpose: computes runoff outflow from a single LID unit.
//  Input:   lidUnit  = ptr. to specific LID unit being analyzed
//           lidProc  = ptr. to generic LID process of the LID unit
//           inflow   = runoff rate captured by LID unit (ft/s)
//           evap     = potential evaporation rate (ft/s)
//           infil    = infiltration rate to native soil (ft/s)
//           maxInfil = max. infiltration rate to native soil (ft/s)
//           tStep    = time step (sec)
//  Output:  lidEvap  = evaporation rate for LID unit (ft/s)
//           lidInfil = infiltration rate for LID unit (ft/s)
//           lidDrain = drain flow for LID unit (ft/s)
//           returns surface runoff rate from the LID unit (ft/s)
//
{
    int    i;
    double x[MAX_LAYERS];        // layer moisture levels
    double xOld[MAX_LAYERS];     // work vector
    double xPrev[MAX_LAYERS];    // work vector
    double xMin[MAX_LAYERS];     // lower limit on moisture levels
    double xMax[MAX_LAYERS];     // upper limit on moisture levels
    double fOld[MAX_LAYERS];     // previously computed flux rates
    double f[MAX_LAYERS];        // newly computed flux rates

    // convergence tolerance on moisture levels (ft, moisture fraction , ft)
    double xTol[MAX_LAYERS] = {STOPTOL, STOPTOL, STOPTOL, STOPTOL};

    double omega = 0.0;          // integration time weighting

    //... define a pointer to function that computes flux rates through the LID
    void (*fluxRates) (double *, double *) = NULL;

    //... save references to the LID process and LID unit
    theLidProc = lidProc;
    theLidUnit = lidUnit;

    //... save evap, max. infil. & time step to shared variables
    EvapRate = evap;
    MaxNativeInfil = maxInfil;
    Tstep = tStep;

    //... store current moisture levels in vector x
    x[SURF] = theLidUnit->surfaceDepth;
    x[SOIL] = theLidUnit->soilMoisture;
    x[STOR] = theLidUnit->storageDepth;
    x[PAVE] = theLidUnit->paveDepth;

    //... initialize layer moisture volumes, flux rates and moisture limits
    SurfaceVolume  = 0.0;
    PaveVolume     = 0.0;
    SoilVolume     = 0.0;
    StorageVolume  = 0.0;
    SurfaceInflow  = inflow;
    SurfaceInfil   = 0.0;
    SurfaceEvap    = 0.0;
    SurfaceOutflow = 0.0;
    PaveEvap       = 0.0;
    PavePerc       = 0.0;
    SoilEvap       = 0.0;
    SoilPerc       = 0.0;
    StorageInflow  = 0.0;
    StorageExfil   = 0.0;
    StorageEvap    = 0.0;
    StorageDrain   = 0.0;
    for (i = 0; i < MAX_LAYERS; i++)
    {
        f[i] = 0.0;
        fOld[i] = theLidUnit->oldFluxRates[i];
        xMin[i] = 0.0;
        xMax[i] = BIG;
        Xold[i] = x[i];
    }

    //... find Green-Ampt infiltration from surface layer
    if ( theLidProc->lidType == POROUS_PAVEMENT ) SurfaceInfil = 0.0;
    else if ( theLidUnit->soilInfil.Ks > 0.0 )
    {
        SurfaceInfil =
            grnampt_getInfil(&theLidUnit->soilInfil, Tstep,
                             SurfaceInflow, theLidUnit->surfaceDepth,
                             MOD_GREEN_AMPT);
    }
    else SurfaceInfil = infil;

    //... set moisture limits for soil & storage layers
    if ( theLidProc->soil.thickness > 0.0 )
    {
        xMin[SOIL] = theLidProc->soil.wiltPoint;
        xMax[SOIL] = theLidProc->soil.porosity;
    }
    if ( theLidProc->pavement.thickness > 0.0 )
    {
        xMax[PAVE] = theLidProc->pavement.thickness;
    }
    if ( theLidProc->storage.thickness > 0.0 )
    {
        xMax[STOR] = theLidProc->storage.thickness;
    }
    if ( theLidProc->lidType == GREEN_ROOF )
    {
        xMax[STOR] = theLidProc->drainMat.thickness;
    }

    //... determine which flux rate function to use
    switch (theLidProc->lidType)
    {
    case BIO_CELL:
    case RAIN_GARDEN:     fluxRates = &biocellFluxRates;   break;
    case GREEN_ROOF:      fluxRates = &greenRoofFluxRates; break;
    case INFIL_TRENCH:    fluxRates = &trenchFluxRates;    break;
    case POROUS_PAVEMENT: fluxRates = &pavementFluxRates;  break;
    case RAIN_BARREL:     fluxRates = &barrelFluxRates;    break;
    case ROOF_DISCON:     fluxRates = &roofFluxRates;      break;
    case VEG_SWALE:       fluxRates = &swaleFluxRates;
                          omega = 0.5;
                          break;
    default:              return 0.0;
    }

    //... update moisture levels and flux rates over the time step
    i = modpuls_solve(MAX_LAYERS, x, xOld, xPrev, xMin, xMax, xTol,
                     fOld, f, tStep, omega, fluxRates);

/** For debugging only ********************************************
    if  (i == 0)
    {
        fprintf(Frpt.file,
        "\n  WARNING 09: integration failed to converge at %s %s",
            theDate, theTime);
        fprintf(Frpt.file,
        "\n              for LID %s placed in subcatchment %s.",
            theLidProc->ID, theSubcatch->ID);
    }
*******************************************************************/

    //... add any surface overflow to surface outflow
    if ( theLidProc->surface.canOverflow || theLidUnit->fullWidth == 0.0 )
    {
        SurfaceOutflow += getSurfaceOverflowRate(&x[SURF]);
    }

    //... save updated results
    theLidUnit->surfaceDepth = x[SURF];
    theLidUnit->paveDepth    = x[PAVE];
    theLidUnit->soilMoisture = x[SOIL];
    theLidUnit->storageDepth = x[STOR];
    for (i = 0; i < MAX_LAYERS; i++) theLidUnit->oldFluxRates[i] = f[i];

    //... assign values to LID unit evaporation, infiltration & drain flow
    *lidEvap = SurfaceEvap + PaveEvap + SoilEvap + StorageEvap;
    *lidInfil = StorageExfil;
    *lidDrain = StorageDrain;

    //... return surface outflow (per unit area) from unit
    return SurfaceOutflow;
}

ChatGPT Version of the SWMM5 Wikipedia Page Introduction

  The EPA Storm Water Management Model (SWMM) is a computer software that simulates the rainfall-runoff-routing process in urban areas. It o...