|
8 | 8 |
|
9 | 9 | import flopy4 |
10 | 10 |
|
| 11 | + |
| 12 | +def plot_head(head, workspace): |
| 13 | + import matplotlib.pyplot as plt |
| 14 | + |
| 15 | + # Plot head results |
| 16 | + plt.figure(figsize=(10, 6)) |
| 17 | + head.isel(layer=0, time=0).plot.contourf() |
| 18 | + plt.title("Filled Contour Plot TWRI Head") |
| 19 | + plt.xlabel("x") |
| 20 | + plt.ylabel("y") |
| 21 | + plt.grid(True) |
| 22 | + plt.savefig(workspace / "head.png", dpi=300, bbox_inches="tight") |
| 23 | + plt.close() |
| 24 | + |
| 25 | + |
11 | 26 | # Timing |
12 | 27 | time = flopy4.mf6.utils.time.Time.from_timestamps( |
13 | 28 | ["2000-01-01", "2000-01-02", "2000-01-03", "2000-01-04"] |
|
28 | 43 | grid = flopy4.mf6.utils.grid.StructuredGrid( |
29 | 44 | nlay=nlay, nrow=nrow, ncol=ncol, top=top, botm=bottom, delr=delr, delc=delc, idomain=idomain |
30 | 45 | ) |
31 | | -dims = {"nper": nper, **dict(grid.dataset.sizes)} # TODO: temporary |
| 46 | +dims = {"nper": nper, "ncpl": nrow * ncol, **dict(grid.dataset.sizes)} # TODO: temporary |
32 | 47 |
|
33 | 48 | # Grid discretization |
34 | 49 | # TODO: xorigin, yorigin |
|
84 | 99 | ) |
85 | 100 |
|
86 | 101 | # Uniform recharge on the top layer |
87 | | -rch_rate = np.stack(np.full((nlay, nrow, ncol), flopy4.mf6.constants.FILL_DNODATA)) |
| 102 | +rch_rate = np.full((nlay, nrow, ncol), flopy4.mf6.constants.FILL_DNODATA) |
88 | 103 | rate = np.repeat(np.expand_dims(rch_rate, axis=0), repeats=nper, axis=0) |
89 | | -rate[0, 0, :] = 3.0e-8 |
| 104 | +rate[0, 0, ...] = 3.0e-8 |
90 | 105 | rch = flopy4.mf6.gwf.Rch(recharge=rate.reshape(nper, -1), dims=dims) |
91 | 106 |
|
92 | 107 | # Output control |
|
103 | 118 | # Wells scattered throughout the model |
104 | 119 | wel_q = -5.0 |
105 | 120 | wel_nodes = [ |
106 | | - [2, 4, 10, -5.0], |
107 | | - [1, 3, 5, -5.0], |
108 | | - [1, 5, 11, -5.0], |
109 | | - [0, 8, 7, -5.0], |
110 | | - [0, 8, 9, -5.0], |
111 | | - [0, 8, 11, -5.0], |
112 | | - [0, 8, 13, -5.0], |
113 | | - [0, 10, 7, -5.0], |
114 | | - [0, 10, 9, -5.0], |
115 | | - [0, 10, 11, -5.0], |
116 | | - [0, 10, 13, -5.0], |
117 | | - [0, 12, 7, -5.0], |
118 | | - [0, 12, 9, -5.0], |
119 | | - [0, 12, 11, -5.0], |
120 | | - [0, 12, 13, -5.0], |
| 121 | + [2, 4, 10], |
| 122 | + [1, 3, 5], |
| 123 | + [1, 5, 11], |
| 124 | + [0, 8, 7], |
| 125 | + [0, 8, 9], |
| 126 | + [0, 8, 11], |
| 127 | + [0, 8, 13], |
| 128 | + [0, 10, 7], |
| 129 | + [0, 10, 9], |
| 130 | + [0, 10, 11], |
| 131 | + [0, 10, 13], |
| 132 | + [0, 12, 7], |
| 133 | + [0, 12, 9], |
| 134 | + [0, 12, 11], |
| 135 | + [0, 12, 13], |
121 | 136 | ] |
122 | 137 | wel = flopy4.mf6.gwf.Wel( |
123 | | - q={"*": {(layer, row, col): wel_q for layer, row, col, wel_q in wel_nodes}}, |
| 138 | + q={"*": {(layer, row, col): wel_q for layer, row, col in wel_nodes}}, |
124 | 139 | dims=dims, |
125 | 140 | ) |
126 | 141 |
|
|
181 | 196 | ) |
182 | 197 |
|
183 | 198 | # Plot head results |
184 | | -head.isel(layer=0, time=0).plot.contourf() |
| 199 | +plot_head(head, workspace) |
| 200 | + |
| 201 | +# UPDATE SIM for array based inputs |
| 202 | + |
| 203 | +# update simulation with array based inputs |
| 204 | +LAYER_NODATA = np.full((nrow, ncol), flopy4.mf6.constants.FILL_DNODATA, dtype=float) |
| 205 | +GRID_NODATA = np.full((nlay, nrow, ncol), flopy4.mf6.constants.FILL_DNODATA, dtype=float) |
| 206 | + |
| 207 | +head = np.repeat(np.expand_dims(GRID_NODATA, axis=0), repeats=nper, axis=0) |
| 208 | +for i in range(nrow): |
| 209 | + for k in range(nlay - 1): |
| 210 | + head[0, k, i, 0] = 0.0 |
| 211 | +chdg = flopy4.mf6.gwf.Chdg( |
| 212 | + print_input=True, |
| 213 | + print_flows=True, |
| 214 | + save_flows=True, |
| 215 | + head=head.reshape(nper, -1), |
| 216 | + dims=dims, |
| 217 | +) |
| 218 | + |
| 219 | +# Drain in the center left of the model |
| 220 | +elev = np.repeat(np.expand_dims(GRID_NODATA, axis=0), repeats=nper, axis=0) |
| 221 | +cond = np.repeat(np.expand_dims(GRID_NODATA, axis=0), repeats=nper, axis=0) |
| 222 | +for j in range(9): |
| 223 | + elev[0, 0, 7, j + 1] = elevation[j] |
| 224 | + cond[0, 0, 7, j + 1] = conductance |
| 225 | +drng = flopy4.mf6.gwf.Drng( |
| 226 | + print_input=True, |
| 227 | + print_flows=True, |
| 228 | + save_flows=True, |
| 229 | + elev=elev.reshape(nper, -1), |
| 230 | + cond=cond.reshape(nper, -1), |
| 231 | + dims=dims, |
| 232 | +) |
| 233 | + |
| 234 | +# well |
| 235 | +q = np.repeat(np.expand_dims(GRID_NODATA, axis=0), repeats=nper, axis=0) |
| 236 | +for layer, row, col in wel_nodes: |
| 237 | + q[0, layer, row, col] = wel_q |
| 238 | +welg = flopy4.mf6.gwf.Welg( |
| 239 | + q=q.reshape(nper, -1), |
| 240 | + dims=dims, |
| 241 | +) |
| 242 | + |
| 243 | +# recharge |
| 244 | +recharge = np.repeat(np.expand_dims(LAYER_NODATA, axis=0), repeats=nper, axis=0) |
| 245 | +recharge[0, ...] = 3.0e-8 |
| 246 | +rcha = flopy4.mf6.gwf.Rcha(recharge=recharge.reshape(nper, -1), dims=dims) |
| 247 | + |
| 248 | +# remove list based inputs |
| 249 | +# TODO: show variations on removing packages |
| 250 | +gwf.chd.remove(chd) |
| 251 | +del gwf.drn[0] |
| 252 | +del gwf.wel[0] |
| 253 | +del gwf.rch[0] |
| 254 | + |
| 255 | +# add array based inputs |
| 256 | +# TODO: needs type checking and list consolidation support (see comments in gwf init) |
| 257 | +gwf.chd = [chdg] |
| 258 | +gwf.drng = [drng] |
| 259 | +gwf.welg = [welg] |
| 260 | +gwf.rcha = [rcha] |
| 261 | + |
| 262 | +# create new workspace |
| 263 | +workspace = Path(__file__).parent / "twri2" |
| 264 | +workspace.mkdir(parents=True, exist_ok=True) |
| 265 | +sim.workspace = workspace |
| 266 | + |
| 267 | +sim.write() |
| 268 | +sim.run() |
| 269 | + |
| 270 | +# Load head results |
| 271 | +head = flopy4.mf6.utils.open_hds( |
| 272 | + workspace / f"{gwf.name}.hds", |
| 273 | + workspace / f"{gwf.name}.dis.grb", |
| 274 | +) |
| 275 | + |
| 276 | +# Plot head results |
| 277 | +plot_head(head, workspace) |
0 commit comments