sandbox/b-flood/ToceFluvial.c

    The Toce fluvial case

    Compilation

    To compile, type in the terminal: qcc ToceFluvial.c -o ToceFluvial.x -lm ~/basilisk/src/kdt/kdt.o

    Introduction

    The entire river is 50 meters long and 11 meters large. The DTM is at a resolution of 5 cm, note that this includes the reproduction of houses. The imposed inlet condition is an hydrograph. The hydrograph is composed of a brutal rising stage from 0 to 210 l.s^{-1} then by a slower and continuous descent phase which reaches up to 60\ l.s^{-1} at the end of the experiment.

    Include and def

    #include "b-flood/saint-venant-topo.h"
    #include "b-flood/manning.h"
    #include "b-flood/inflow.h"
    #include "b-flood/hydro.h"
    #include "terrain.h"
    #include "input.h"
    
    #define MAXLEVEL 10 // 1024 Volume
    #define MINLEVEL 6
    #define EMAXE 5e-4
    
    int nf, nc, ncell;
    timer t0;

    Parameters

    int main()
    {
      n = 0.0162;
      L0 = 43.4;
      X0 = 0.1;
      Y0 = 0;
      G = 9.81;
      dry = 1e-6;
      N = 1 << MAXLEVEL; // Which is equivalent to N = 2^(maxlevel)
      run();
    }
    
    // The case lasts 180 seconds
    event stop (t = 180)
      fprintf (stderr, "# The end\n");

    Initial condition

    event init (i = 0)
    {
      // We record the topography in a special way (k-tree) so that we can
      // use adaptive refinement on it.  
      terrain (zb, "./Topo/topo-house", NULL);
      
      // We have to set a time step because there is no water at the beginning.
      DT = 1;
      
      t0 = timer_start();
      double dx = L0/N;
    
      // We set the interval through which the water flow will come in.
      foreach()
        if (y <= 8.4 && y >= 5 && x <= 8*dx)
          river[] = 1;
      boundary ({river});
    }

    Inflow boundary condition

    On the left, we impose the flow rate using the “discharge” function.

    reset
    set xlabel 'T(s)' 
    set ylabel 'Inflow (cumsec)' 
    set xtics; set ytics
    set key bot
    plot './hydro.asc' w l t'hydrograph'
    Hydrograph (script)

    Hydrograph (script)

    u.t[left] = dirichlet(0);
    u.n[left] = neumann(0);
    
    double l1, eta1, vola = 0;
    event bound_left( i++ )
    {
      l1 =  hydrograph ("hydro.asc", 1);
      if (l1 < 0)
        l1 = 0;
      eta1 = eta_b(l1,left,1);
      
      h[left] = dirichlet( max( river[] == 1 ? eta1 - zb[] : 0 , 0) );
      eta[left] = dirichlet( max( river[] == 1 ? eta1 : zb[]  , zb[]) );
    
      double vol = 0;
      foreach(reduction(+:vol)){
        if( h[] > dry )
          vol += h[] * sq(Delta);
      }
      double Q = 0;
      if( dt > 0 )
        Q =  (vol- vola)/dt;
      vola = vol;
     
      static FILE * fpp = fopen ("eta.dat", "w");
       if (i == 0)
         fprintf (fpp, "#t Q Qread EtaImp\n");
      fprintf (fpp, "%lf %lf %lf %lf \n", t, Q, l1, eta1);
      fflush (fpp);  
    }

    Outflow boundary conditions

    We set a free exit condition on the right edge of the domain.

    u.t[right] = neumann(0);
    u.n[right] = neumann(0);
    h[right] = neumann(0);
    eta[right] = neumann(0);

    We take care to reduce the maximum time step just before the water inlet starts.

    event timestepreduce (t = 17) {
      DT = 0.01;
    }

    Adaptive refinement

    The adaptive refinement starts just before the water inlet starts.

    event adapt (t = 17; i++)
    {
      scalar nh[];
      foreach()
        nh[] = h[] > dry ? h[] : 0;
      boundary ({nh});
      astats s = adapt_wavelet ({nh}, (double[]){EMAXE}, MAXLEVEL, MINLEVEL);
      nc += s.nc;
      nf += s.nf;
    }

    Logfile

    event logfile (i += 10)
    {
      timing tr = timer_timing (t0, i, 0, NULL);
      stats s = statsf (h);
      scalar v[];
      foreach()
        v[] = norm(u);
      
      stats no = statsf (v);
      if( i == 0 )
        fprintf (stderr, "#1t 2treal 3i 4h.min 5h.max 6h.sum 7u.min 8u.max 9dt\n");  
      fprintf (stderr, "%g %g %d %g %g %g %g %g %g\n",
    	   t,tr.real, i, s.min, s.max, s.sum,  no.min, no.max, dt);
    }

    Gauges

    We record the water level at the same location than the experiment

    Gauge gauges[] = {  
      // gauge   x         y       zb
      {"S2",0.280560,7.585584, "#S2"},
      {"S4",4.255610,7.745400, "#S4"},
      {"S6S",6.753537,9.831888, "#S6S"},
      {"S6D",7.552486,7.696863, "#S6D"},
      {"S8D",10.743772,7.788068, "#S8D"},
      {"P1",2.113886,7.866009, "#P1"},
      {"P2",3.931183,8.893101, "#P2"},
      {"P3",4.527122,6.587255, "#P3"},
      {"P4",7.086251,8.768313, "#P4"},
      {"P5",10.163515,10.218714, "#P5"},
      {"P8",14.950365,11.804039, "#P8"},
      {"P9",15.684258,13.802726, "#P9"},
      {"P10",18.190768,10.429219, "#P10"},
      {"P13",19.814693,11.984270, "#P13"},
      {"P18",23.848138,14.744612, "#P18"},
      {"P19",25.469928,16.186758, "#P19"},
      {"P21",30.442363,18.357176, "#P21"},
      {"P23",36.466741,18.750427, "#P23"},
      {"P24",39.024308,22.827062, "#P24"},
      {"P25",40.443587,21.238121, "#P25"},
      {"P26",40.965033,26.182320, "#P26"},
      {NULL}
    };
    event gauges1 (t += 1) output_gauges (gauges, {h});

    Gauges results

    set term svg enhanced size 800,400 font ",10"
    set ylabel 'Level (m)' 
    set xtics; set ytics
    set multiplot
    set size .95,.35
    set key bot
    set origin 0.02, 0.6
    plot 'P1' w lp t'P1 - numerical', 'P1.ref' w lp t'P1 - measured'
    set origin 0.02, 0.3
    plot 'P2' w lp t'P2 - numerical', 'P2.ref' w lp t'P2 - measured'
    set origin 0.02, .01
    set xlabel 'T(s)' 
    plot 'P3' w lp t'P3 - numerical', 'P3.ref' w lp t'P3 - measured'
    unset multiplot
    Gauges P1, P2 and P3 (script)

    Gauges P1, P2 and P3 (script)

    set term svg enhanced size 800,400 font ",10"
    set ylabel 'Level (m)' 
    set xtics; set ytics
    set multiplot
    set size .95,.35
    set key bot
    set origin 0.02, 0.6
    plot 'P4' w lp t'P4 - numerical', 'P4.ref' w lp t'P4 - measured'
    set origin 0.02, 0.3
    plot 'P5' w lp t'P5 - numerical', 'P5.ref' w lp t'P5 - measured'
    set origin 0.02, .01
    set xlabel 'T(s)' 
    plot 'P8' w lp t'P8 - numerical', 'P8.ref' w lp t'P8 - measured'
    unset multiplot
    Gauges P4, P5 and P8 (script)

    Gauges P4, P5 and P8 (script)

    set term svg enhanced size 800,400 font ",10"
    set ylabel 'Level (m)' 
    set xtics; set ytics
    set multiplot
    set size .95,.35
    set key bot
    set origin 0.02, 0.6
    plot 'P9' w lp t'P9 - numerical', 'P9.ref' w lp t'P9 - measured'
    set origin 0.02, 0.3
    plot 'P10' w lp t'P10 - numerical', 'P10.ref' w lp t'P10 - measured'
    set origin 0.02, .01
    set xlabel 'T(s)' 
    plot 'P13' w lp t'P13 - numerical', 'P13.ref' w lp t'P13 - measured'
    unset multiplot
    Gauges P9, P10 and P13 (script)

    Gauges P9, P10 and P13 (script)

    set term svg enhanced size 800,400 font ",10"
    set ylabel 'Level (m)' 
    set xtics; set ytics
    set multiplot
    set size .95,.35
    set key bot
    set origin 0.02, 0.6
    plot 'P18' w lp t'P18 - numerical', 'P18.ref' w lp t'P18 - measured'
    set origin 0.02, 0.3
    plot 'P19' w lp t'P19 - numerical', 'P19.ref' w lp t'P19 - measured'
    set origin 0.02, .01
    set xlabel 'T(s)' 
    plot 'P21' w lp t'P21 - numerical', 'P21.ref' w lp t'P21 - measured'
    unset multiplot
    Gauges P18, P19 and P21 (script)

    Gauges P18, P19 and P21 (script)

    set term svg enhanced size 800,400 font ",10"
    set ylabel 'Level (m)' 
    set xtics; set ytics
    set multiplot
    set size .95,.35
    set key bot
    set origin 0.02, 0.6
    plot 'P23' w lp t'P23 - numerical', 'P23.ref' w lp t'P23 - measured'
    set origin 0.02, 0.3
    plot 'P24' w lp t'P24 - numerical', 'P24.ref' w lp t'P24 - measured'
    set origin 0.02, .01
    set xlabel 'T(s)' 
    plot 'P25' w lp t'P25 - numerical', 'P25.ref' w lp t'P25 - measured'
    unset multiplot
    Gauges P23, P24 and P25 (script)

    Gauges P23, P24 and P25 (script)

    reset
    set term svg enhanced size 800,400 font ",10"
    set ylabel 'Level (m)' 
    set xtics; set ytics
    set multiplot
    set size .95,.35
    set key bot
    set origin 0.02, 0.6
    plot 'P26' w lp t'P26 - numerical', 'P26.ref' w lp t'P26 - measured'
    set origin 0.02, 0.3
    plot 'S2' w lp t'S2 - numerical', 'S2.ref' w lp t'S2 - measured'
    set origin 0.02, .01
    set xlabel 'T(s)' 
    plot 'S4' w lp t'S4 - numerical', 'S4.ref' w lp t'S4 - measured'
    unset multiplot
    Gauges P26, S2 and S4 (script)

    Gauges P26, S2 and S4 (script)

    reset
    set term svg enhanced size 800,400 font ",10"
    set ylabel 'Level (m)' 
    set xtics; set ytics
    set multiplot
    set size .95,.35
    set key bot
    set origin 0.02, 0.6
    plot 'S6D' w lp t'S6D - numerical', 'S6D.ref' w lp t'S6D - measured'
    set origin 0.02, 0.3
    plot 'S6S' w lp t'S6S - numerical', 'S6S.ref' w lp t'S6S - measured'
    set origin 0.02, .01
    set xlabel 'T(s)' 
    plot 'S8D' w lp t'S8D - numerical', 'S8D.ref' w lp t'S8D - measured'
    unset multiplot
    Gauges S6D, S6S and S8D (script)

    Gauges S6D, S6S and S8D (script)

    Movies

    We record movies of the water depth, the velocity and the level of refinement.

    Evolution of the water level

    Evolution of the Froude number. Dark blue is zero, dark red is two.

    Evolution of the refinement level

    Evolution of the water level close to town #1

    Evolution of the refinement level close to town #1

    Evolution of the water level close to town #2

    Evolution of the refinement level close to town #2

    event movies ( t= 17; t += 0.1 )
    {
      scalar m[], v[], fr[];
      
      foreach(){
        v[] = norm(u);
        m[] = (h[] > dry ) - 0.5;
        fr[] = h[] > dry ? v[]/sqrt(G*h[]) : 0;
      }    
      boundary ({m,v,fr});
      
      output_ppm (h, mask = m, min = 0, max = 0.4, n = N, linear = true, file = "height.mp4");
      output_ppm (h, mask = m, min = 0, max = 0.4, n = N, linear = true,
    	      box = {{0,5},{12.5,12.5}}, file = "height-town1.mp4"); 
      output_ppm (h, mask = m, min = 0, max = 0.4, n = N, linear = true,
    	      box = {{15,9},{25,19}}, file = "height-town2.mp4");
      
      
    
      output_ppm (v,  mask = m, min = 0, max = 3, n = N, linear = true, file = "vel.mp4");
    
      output_ppm (fr, mask = m, min = 0, max = 2, n = N, linear = true, file = "froude.mp4");
      
      scalar l = m;
      foreach()
        l[] = level;
      
      output_ppm (l, min = MINLEVEL, max = MAXLEVEL, n = N, file = "level.mp4");
      output_ppm (l, min = MINLEVEL, max = MAXLEVEL, n = N,
    	      box = {{0,5},{12.5,12.5}}, file = "level-town1.mp4");
      output_ppm (l, min = MINLEVEL, max = MAXLEVEL, n = N,
    	      box = {{15,9},{25,19}}, file = "level-town2.mp4");
    }
    
    
    event snap (t = 65)
    {
      static FILE * rph = fopen ("raster_h-t65.asc", "w");
      output_grd (h, rph);
    
      scalar m[], v[];
        
      foreach(){
        v[] = norm(u);
        m[] = (h[] > dry ) - 0.5;
      }    
      boundary ({m,v});
      
      static FILE * rpu = fopen ("raster_v-t65.asc", "w");
      output_grd (v, rpu);
    }
    
    event ending (t = end)
    {
      static FILE * rph = fopen ("raster_h.asc", "w");
      output_grd (h, rph);
    
      scalar m[], v[];
        
      foreach(){
        v[] = norm(u);
        m[] = (h[] > dry ) - 0.5;
      }    
      boundary ({m,v});
      
      static FILE * rpu = fopen ("raster_v.asc", "w");
      output_grd (v, rpu);
    }

    Figures

    Here we record the photos representing the dynamics of adaptive refinement and water level used in the scientific article.

    event figures (t = 17; t <= 67; t += 2)
    {
      scalar m[], etam[];
      foreach() {
        etam[] = eta[]*(h[] > dry);
        m[] = etam[] - zb[];
      }
      boundary ({m, etam});
      char name[80];
      sprintf (name, "h-%g.png", t);
      output_ppm (h, min = 0, max = 0.4, mask = m, file = name, n = 1024,
    	      linear = true,
    	      opt = "-fill white -opaque black");
        
      sprintf (name, "level-%g.png", t);
      scalar l[];
      foreach()
        l[] = level;
      output_ppm (l, min = MINLEVEL, max = MAXLEVEL, file = name, n = 1024,
    	      linear = false,);
    }

    References