/*
 * SUMMARY:      data.h - header file with data structures
 * USAGE:        Part of DHSVM
 *
 * AUTHOR:       Bart Nijssen
 * ORG:          University of Washington, Department of Civil Engineering
 * E-MAIL:       nijssen@u.washington.edu
 * ORIG-DATE:    Apr-1996
 * Last Change: Thu Dec  5 08:26:45 2002 by Scott Waichler <waichler@tuff.pnl.gov>
 * DESCRIPTION:  header file with data structures
 * DESCRIP-END.
 * FUNCTIONS:    
 * COMMENTS:     
 */

/* 	$Id: data.h,v 1.3 2001/05/15 17:30:27 waichler Exp $	 */

#ifndef DATA_H
#define DATA_H

#include "typenames.h"
#include "Calendar.h"

typedef struct {
    int N;			/* Northing */
    int E;			/* Easting */
} COORD;

typedef struct {
  char FileName[BUFSIZE+1];
  FILE *FilePtr;
} FILES;

typedef struct {
  int ID;			/* Index for variable to dump */
  int Layer;			/* Layer for which to dump */
  char Name[BUFSIZE+1];		/* Variable Name */
  char LongName[BUFSIZE+1];	/* Long name */
  char Format[BUFSIZE+1];	/* Output format (for netcdf files) */
  char Units[BUFSIZE+1];	/* Units */
  uchar Resolution;		/* Resolution at which to dump */
  int N;			/* Number of timesteps for which to dump */
  float MinVal;			/* Lowest value for indexing low resolution */
  float MaxVal;			/* Highest value for indexing low resolution */
  char FileName[BUFSIZE+1];	/* File to write dump to */
  char FileLabel[BUFSIZE+1];	/* File label */
  int NumberType;		/* Number type of variable */
  DATE *DumpDate;		/* Date(s) at which to dump */
} MAPDUMP;

typedef struct {
  COORD Loc;			/* Location for which to dump */
  FILES OutFile;		/* Files in which to dump */
} PIXDUMP;


typedef struct {
  char Path[BUFSIZE+1];		/* Path to dump to */
  char InitStatePath[BUFSIZE+1]; /* Path for initial state */
  FILES Aggregate;		/* File with aggregated values for entire
                                   basin */
  FILES Balance;
  FILES Stream;
  FILES List;
  int NStates;			/* Number of model state dumps */
  DATE *DState;			/* Array with dates on which to dump state */
  int NPix;			/* Number of pixels for which to output
				   timeseries */
  PIXDUMP *Pix;			/* Array with info on pixels for which to 
				   output timeseries */
  int NMaps;			/* Number of variables for which to output 
				   maps */
  MAPDUMP *DMap;		/* Array with info on each map to output */
} DUMPSTRUCT;

typedef struct {
  float ETot;			/* Total amount of evapotranspiration */
  float *EPot;			/* Potential transpiration from each 
				   vegetation/soil layer */
  float *EAct;			/* Actual transpiration from each vegetation/ 
				   soil layer */
  float *EInt;			/* Evaporation from interception for each 
				   vegetation layer */
  float **ESoil;		/* Transpiration for each vegetation layer 
				   from each soil zone */
  float EvapSoil;		/* Evaporation from the upper soil layer */
} EVAPPIX;

typedef struct {
  int TimeStep;
  float Fraction;
} UNITHYDR;

typedef struct {
    int MaxTravelTime;
    int TotalWaveLength;
    int *WaveLength;
} UNITHYDRINFO;

typedef struct {
  char Const[BUFSIZE+1];	/* Filename for main input file  */
  char RadMapPath[BUFSIZE+1];	/* Path and start of filename for rad files */
  char RadTablePath[BUFSIZE+1]; /* Same for rad tables */
  char RadarFile[BUFSIZE+1];	/* File with radar precipitation */
  char MM5Temp[BUFSIZE+1];	/* File with MM5 temperature (C) */
  char MM5Humidity[BUFSIZE+1];	/* File with MM5 humidity (%) */
  char MM5Wind[BUFSIZE+1];	/* File with MM5 wind speed (m/s) */
  char MM5ShortWave[BUFSIZE+1];	/* File with MM5 shortwave (W/m2)*/
  char MM5LongWave[BUFSIZE+1];	/* File with MM5 longwave (W/m2) */
  char MM5Pressure[BUFSIZE+1];	/* File with MM5 pressure (Pa) */
  char MM5Precipitation[BUFSIZE+1]; /* File with MM5 precipitation 
				       (m/timestep) */
  char **MM5SoilTemp;		/* Files with MM5 soil temperatures (C) */
  char PrecipLapseFile[BUFSIZE+1]; /* File with precipitation 
					  lapse rate map */
  char WindMapPath[BUFSIZE+1];	/* File with wind factors */
} INPUTFILES;

typedef struct {
  int NTypes;
  int *NLayers;
  int MaxLayers;
} LAYER;

typedef struct {
  float Tair;			/* Air temperature (C) */
  float Rh;			/* Relative humidity (%) */
  float Wind;			/* Wind (m/s) */
  float Sin;			/* Incoming shortwave (W/m^2) */
  float SinBeam;		/* Incoming beam radiation (W/m^2) */
  float SinDiffuse;		/* Incoming diffuse radiation (W/m^2) */
  float Lin;			/* Incoming longwave (W/m^2) */
  float AirDens;		/* Air density on kg/m^3 */
  float Lv;			/* Latent heat of vaporization (J/kg) */
  float Press;			/* Atmospheric pressure (Pa) */
  float Gamma;			/* Psychrometric constant (Pa/C) */
  float Es;			/* Saturated vapor pressure (Pa) */
  float Eact;			/* Actual vapor pressure (Pa) */
  float Slope;			/* Slope of vapor pressure curve (Pa/C) */
  float Vpd;			/* Vapor pressure deficit (Pa) */
} PIXMET;

typedef struct {
  char System[BUFSIZE+1];	/* Coordinate system */
  double Xorig;			/* X coordinate of Northwest corner */
  double Yorig;			/* Y coordinate of Northwest corner */
  int X;			/* Current x position */
  int Y;			/* Current y position */
  int NX;			/* Number of pixels in x direction */
  int NY;			/* Number of pixels in y direction */
  float DX;			/* Pixel spacing in x-direction */
  float DY;			/* Pixel spacing in y-direction */
  float DXY;			/* Pixel spacing in diagonal */
  int OffsetX;			/* Offset in x-direction compared to basemap */
  int OffsetY;			/* Offset in y-direction compared to basemap */
  int xneighbor[NDIRS];
  int yneighbor[NDIRS];
  int NumCells;           /* Number of cells within the basin */
  int **OrderedCellsRowCol;   /* Matrix that is NumCells x 2 in size; 
                                 [i][1] is y-coordinate (row); [i][2] is x-coordinate (col) */
} MAPSIZE;

typedef struct {
  float Tair;			/* Air temperature (C) */
  float Rh;			/* Relative humidity (%) */
  float Wind;			/* Wind (m/s) */
  int WindDirection;            /* Wind direction, used when 
                                   WindSource == MODEL  */
  float Sin;			/* Incoming shortwave (W/m^2) */
  float SinBeamObs;		/* Observed incoming beam radiation (W/m^2) */
  float SinDiffuseObs;		/* Observed incoming diffuse radiation 
				   (W/m^2) */
  float SinBeamMod;		/* Modeled incoming beam radiation (W/m^2) */
  float SinDiffuseMod;		/* Modeled incoming diffuse radiation (W/m^2) */
  float BeamRatio;		/* Ratio of observed beam to modeled beam */
  float DiffuseRatio;		/* Ratio of observed diffuse to modeled 
				   diffuse */
  float Lin;			/* Incoming longwave (W/m^2) */
  float ClearIndex;		/* Cloudiness index */
                                /* The following is a hack, and needs to be
                                   replaced by a better method,
                                   WORK IN PROGRESS */
  float Precip;			/* Rainfall if available (m) */
  float Tsoil[3];               /* Soil temperature in upper three layers */
  float TempLapse[5];              /* Temperature lapse rate (C/m) */
  float PrecipLapse[5];            /* Elevation Adjustment Factor for Precip */
  char *BeamCode;		/* Direct beam solar radiation class 
                                   for each timestep */
  char *DiffuseCode;		/* Diffuse solar radiation class 
                                   for each timestep */
} MET;

typedef struct {
  char Name[BUFSIZE+1];		/* Station name */
  COORD Loc;			/* Station locations */
  int NPrecipLapse;		/* Number of Precip Lapse Rates */
  int NTempLapse;		/* Number of Temperature Lapse Rates */
  float ElevBreak[5];
  float Elev;			/* Station elevations */
  float PrismPrecip[12];        /* MonthlyPrism Precip for each station if outside=TRUE*/
  uchar IsWindModelLocation;	/* Only used in case the wind model option is
				   specified.  In that case this field is TRUE
				   for one (and only one) station, and FALSE 
				   for all others */
  FILES MetFile;		/* File with observations */
  MET Data;
} METLOCATION;

typedef struct {
  int FileFormat;               /* File format indicator, BIN or HDF */
  int RadType;                  /* Type of radiation calculations to use, IPW
                                   or INLINE */
  int HasNetwork;               /* Flag to indicate whether roads and/or
                                   channels are imposed on the model area,
                                   TRUE if NETWORK, FALSE if UNIT_HYDROGRAPH */
  int PrecipType;               /* Precipitation source indicator, either
                                   RADAR or STATION */
  int Prism;                    /* If TRUE, user supplied PRISM maps will be 
				   used to interpolate precipitation */
  int PrecipLapse;              /* Whether the precipitation lapse rate is
                                   CONSTANT or VARIABLE */
  int TempLapse;                /* Whether the temperature lapse rate is
                                   CONSTANT or VARIABLE */
  int CressRadius;
  int   CressStations;
  int WindSource;		/* Wind source indicator, either MODEL or 
				   STATION */
  int HeatFlux;                 /* Specifies whether a sensible heat flux 
                                   should be calculated, TRUE or FALSE */
  int FlowGradient;             /* Specifies whether the flow gradient is based
                                   on the terrain elevation (TOPOGRAPHY) or the 
                                   water table elevation (WATERTABLE).  The 
                                   TOPOGRAPHY method is much faster, since the 
                                   flow direction and gradient do not have to 
                                   be recalculated every timestep */
  int ReadFlowDir;              /* TRUE if reading flow direction flow file, 
                                   FALSE otherwise */
  int Extent;                   /* Specifies the extent of the model run,
                                   either POINT or BASIN */
  int Interpolation;
  int MM5;			/* TRUE if MM5 interface is to be used, FALSE
				   otherwise */
  int QPF;                     /* TRUE if QPF override, else FALSE*/
  int PointX;                  /* X-index of point to model in POINT mode */
  int PointY;                  /* Y-index of point to model in POINT mode */
  int Snotel;                  /* if TRUE then station veg = bare for output*/
  int Outside;                 /* if TRUE then all listed met stats are used */
  int Rhoverride;              /* if TRUE then RH=100% if Precip>0*/
  int ReadState;               /* if TRUE then read initial state conditions from files */
  int Infiltration;            /* VARIABLE with soil moisture, or CONSTANT */
  int HydraulicRouting;        /* Use the named scheme for overland flow routing;
                                    LINEAR=constant velocity.   */
  int ChannelRouting;          /* LINEAR for linear reservoir method for routing streamflow;
                                  POWERLAW for powerlaw storage-discharge method; FTABLE for ftable method.  
                                  Only FTABLE method can potentially result in channel infiltration. */
  int Groundwater;             /* if TRUE use lower groundwater layer */
  int FrozenSoil;              /* if TRUE use lower groundwater layer */
} OPTIONSTRUCT;
 
typedef struct {
  float Precip;			/* Total amount of precipitation at pixel (m) */
  float RainFall;               /* Amount of rainfall (m) */
  float SnowFall;               /* Amount of snowfall (m) */
  float *IntRain;		/* Rain interception by each vegetation layer
                                   (m) */
  float *IntSnow;		/* Snow interception by each vegetation layer
                                   (m) */
  float TempIntStorage;         /* Temporary snow and rain interception storage,
                                   used by MassRelease() */
  float CumPrecip;  	/* Cumulative amount of precipitation at pixel (m) SRW 12/05/02. */
} PRECIPPIX;

typedef struct {
  float Precip;			/* Radar precipitation for current bin */
} RADARPIX;

typedef struct {
  char *BeamCode;		/* Direct beam solar radiation class 
                                   for each timestep */
  float Beam;			/* Beam value */
  char *DiffuseCode;		/* Diffuse solar radiation class 
                                   for each timestep */
  float Diffuse;		/* Diffuse value */
} RADCLASSPIX;

typedef struct {
  float NetShort[2];            /* Shortwave radiation for vegetation surfaces 
				   and ground/snow surface W/m2 */
  float LongIn[2];              /* Incoming longwave radiation for vegetation
                                   surfaces and ground/snow surface W/m2 */
  float LongOut[2];             /* Outgoing longwave radiation for vegetation
                                   surfaces and ground/snow surface W/m2 */
  float PixelNetShort;          /* Net shortwave for the entire pixel W/m2 */
  float PixelLongIn;            /* Incoming longwave for entire pixel W/m2 */
  float PixelLongOut;           /* Outgoing longwave for entire pixel W/m2 */
} PIXRAD;

typedef struct {
  float **Beam;			/* Direct solar radiaton for a given class and
				   timestep */
  float **Diffuse;		/* Diffuse solar radiation for a given class
				   and timestep */
  int NClasses;			/* Number of radiation classes */
  int Start;			/* First timestep of day for which sun above
				   horizon */
  int End;			/* Last timestep of day for which sun above 
				   horizon */
} RADTABLE;

typedef struct {
  float Width;                  /* Width of road or channel cut (m) */
  float BankHeight;             /* Height of road or channel cut (m) */
  int CutBankZone;              /* Number of the soil layer that contains the
                                   bottom of the road/channel cut */
  float *PercWidth;             /* Width of percolation zone for each soil
                                   layer, corrected for the road/channel cut,
                                   divided by the grid cell width (0-1)  */
  float *Adjust;                 /* Array with coefficients to correct for
                                   loss of soil storage due to
                                   channel/road-cut for each soil layer.
                                   Multiplied with RootDepth to give the zone
                                   thickness for use in calculating soil
                                   moisture */
  uchar fraction;               /* flow fraction intercepted by road channel */
} ROADSTRUCT;


typedef struct {
  uchar HasSnow;		/* Snow cover flag */
  uchar SnowCoverOver;		/* Flag overstory can be covered */
  unshort LastSnow;		/* Days since last snowfall */
  float Swq;			/* Snow water equivalent */
  float Melt;			/* Snow Melt */
  float Outflow;                /* Snow pack outflow (m) */
  float PackWater;		/* Liquid water content of snow pack */
  float TPack;			/* Temperature of snow pack */
  float SurfWater;		/* Liquid water content of surface layer */
  float TSurf;			/* Temperature of snow pack surface layer */
  float ColdContent;		/* Cold content of snow pack */
  float Albedo;			/* Albedo of snow pack */
  float Depth;			/* Snow depth */
  float VaporMassFlux;          /* Vapor mass flux to/from snow pack
                                   (m/timestep) */
  float CanopyVaporMassFlux;    /* Vapor mass flux to/from intercepted snow in
                                   the canopy (m/timestep) */
} SNOWPIX;

typedef struct {
  int Soil;			/* Soil type */
  float Depth;			/* Depth of total soil zone, including all root
				   zone layers, and the saturated zone */
  float *Moist;			/* Soil moisture content in layers */
  float *Perc;			/* Percolation from layers */
  float *Temp;			/* Temperature in each layer (C) */
  float TableDepth;		/* Depth of water table below ground surface 
				   (m) */
  float SatThickness; /* height of water table above bottom of upper (soil) zone (m) */
  float WaterLevel;		/* Absolute height of the watertable above 
				   datum (m), i.e. corrected for terrain
				   elevation */
  float SatFlow;		/* amount of saturated flow generated */
  float Runoff;			/* amount of surface runoff generated from
                                   HOF and Return flow */ 
  float ChannelInt;             /* amount of subsurface flow intercepted by
                                   the channel */ 
  float RoadInt;                /* amount of water intercepted by the road */
  float TSurf;			/* Soil surface temperature */
  float Qnet;			/* Net radiation exchange at surface */
  float Qrest;                  /* Rest term for energy balance (should be 0) */
  float Qs;			/* Sensible heat exchange */
  float Qe;			/* Latent heat exchange */
  float Qg;			/* Ground heat exchange */
  float Qst;			/* Ground heat storage */
  float Ra;                     /* Soil surface aerodynamic resistance (s/m) */
  float startRunoff;
  float GwRecharge;  /* percolation downward from the upper saturated zone (m) in the timestep */
  float CumGwRecharge; /* cumulative percolation downward from the upper saturated zone (m) */
  float CumChannelLoss; /* cumulative infiltration into upper saturated zone from channel (m) */
  float QuickVol;
} SOILPIX;

typedef struct {
  char Desc[BUFSIZE+1];	/* Soil type */
  int Index;
  int NLayers;			/* Number of soil layers */
  float Albedo;			/* Albedo of the soil surface */
  float *Porosity;		/* Soil porosity for each layer */
  float *PoreDist;		/* Pore size distribution for each layer */
  float *Press;			/* Soil bubling pressure for each layer */
  float *FCap;			/* Field capacity for each layer  */
  float *WP;			/* Wilting point for each layer */
  float *Dens;			/* Soil density (kg/m^3) */
  float *Ks;			/* Saturated hydraulic conductivity 
				   (vertical) for each layer */
  float KsLat;			/* Saturated hydraulic conductivity 
				   (lateral) */
  float KsLatExp;		/* Exponent for vertical change of KsLat */
  float *KhDry;			/* Thermal conductivity for dry soil 
                                   (W/(m*K)) */
  float *KhSol;			/* Effective solids thermal conductivity
                                   (W/(M*K)) */
  float *Ch;			/* Heat capacity for soil medium */
  float MaxInfiltrationRate;    /* Maximum infiltration rate for upper layer
                                   (m/s) */
  float infiltrationCoeff;  /* coefficient for time varing infiltration */
  float infiltrationExp;    /* exponent for time varing infiltration */
  float quickflowCoeff;
  float quickflowExp;
  float maxResistance;
  float resistanceCoeff;
  float groundwaterKs;
  float groundwaterKsLat;
  float baseLayerKs;
  float maxGroundMelt;   /* maximum rate of snowmelt from ground heat flux */
} SOILTABLE;

typedef struct {
  float Freeze;			/* albedo when surface temperature below 0 C */
  float Thaw;			/* albedo when surface temperature above 0 C */
} SNOWTABLE;

typedef struct {
  float Dem;			/* Elevations */
  uchar Mask;			/* Mask for modeled area */
  unshort Travel;		/* Travel time */
  float Grad;			/* Sum of downslope slope-width products */
  float Slope;                  /* Land surface slope */
  float Aspect;                 /* Land surface slope direction */
  float FlowGrad;               /* Magnitude of subsurface flow gradient
                                   slope * width*/
  unsigned char Dir[NDIRS];	/* Fraction of flux moving in each direction
                                 */
  unsigned int TotalDir;        /* Sum of Dir array */
  double Area;                  /* Cell area in m^2 */
} TOPOPIX;

typedef struct {
  int Veg;			/* Vegetation type */
  float Tcanopy;                /* Canopy temperature (C) */
} VEGPIX;
  
typedef struct {
  char Desc[BUFSIZE+1];	/* Vegetation type */
  int Index;
  int NVegLayers;      		/* Number of vegetation layers */
  int NSoilLayers;		/* Number of soil layers */
  unsigned char OverStory;      /* TRUE if there is an overstory */
  unsigned char UnderStory;     /* TRUE if there is an understory */
  float *Height;		/* Height of vegetation (in m) */
  float *Fract;			/* Fractional coverage */
  float *LAI;			/* One Sided Leaf Area Index */
  float *LAISummer;		/* Summer LAI */
  float *LAIWinter;		/* Winter LAI */
  float **MonthLAI;     /* Monthly LAI values */
    
  float *MaxInt;		/* Maximum interception storage (m) */
  float *RsMax;			/* Maximum stomatal resistance */
  float *RsMin;			/* Minimum stomatal resistance */
  float *MoistThres;		/* Soil moisture threshold above which soil 
				   moisture does not restrict transpiration */
  float *VpdThres;		/* Vapor pressure deficit threshold above which
				   stomatal closure occurs (Pa) */
  float **RootFract;		/* Fraction of roots in each soil layer */
  float *RootDepth;		/* Depth of root zones */
  float TotalDepth;             /* total depth of all root zones */
  float Atten;			/* Canopy attenuation for radiation */
  float *Rpc;			/* ?? */
  float *Albedo;		/* Albedo for each vegetation layer */
  float Cn;			/* Canopy attenuation coefficient for wind 
				   profile */
  float MaxSnowInt;             /* Maximum snow interception capacity for the overstory*/
  float MDRatio;                /* Ratio of Mass Release to Meltwater drip from int snow*/
  float SnowIntEff;             /* Efficiency of snow interception process */
  float Ra[2];                  /* Aerodynamic resistance in the absence of 
				   snow  */ 
  float RaSnow;                 /* Aerodynamic resistance for the lower boundary
                                   in the presence of snow */
  float Trunk;                  /* Fraction of overstory height that identifies
                                   the top of the trunk space */
  float U[2];                   /* Wind speed profile (m/s) */
  float USnow;                  /* wind speed 2, above snow surface (m/s) */
} VEGTABLE;

typedef struct {
  EVAPPIX Evap;
  PRECIPPIX Precip;
  PIXRAD Rad;
  RADCLASSPIX RadClass;
  SNOWPIX Snow;
  SOILPIX Soil;
  float SoilWater;
  float CanopyWater;
  float Runoff;
  float ChannelInt;
  float RoadInt;
  unsigned long Saturated;
  float CulvertReturnFlow;
  float CulvertToChannel;
  float RunoffToChannel;
  float MeanTair;
  double BasinArea;
  int ActiveCells;
  float GwDepth;
  float GwToChannel;
  float GwDeepLoss;
  float channelLoss;
  float frozenSoilHeatFlux;
} AGGREGATED;

typedef struct {
  float StartWaterStorage;
  float OldWaterStorage;
  float CumPrecipIn;
  float CumET;
  float CumRunoff;
  float CumChannelInt;
  float CumRoadInt;
  float CumSnowVaporFlux;
  float CumCulvertReturnFlow;
  float CumCulvertToChannel;
  float CumRunoffToChannel;
  float CumSoilEvap;
  float CumGwRecharge;
  float CumQuickVol;
  float CumGwDeepLoss;
  float CumGwToChannel;
  float CumChannelLoss;
} WATERBALANCE;

typedef struct {
  float accum_precip;
  float air_temp;
  float wind_speed;
  float humidity;
} MET_MAP_PIX;

typedef struct {
  float SoilTemp;
  float SoilMoistureFactor;
  float GroundwaterDepth;
} STATESTRUCT;


#endif
