Source code for pydfnworks.dfnGen.meshing.mesh_dfn

"""
.. module:: mesh_dfn.py
   :synopsis: meshing driver for DFN 
.. moduleauthor:: Jeffrey Hyman <jhyman@lanl.gov>

"""

import os
import sys
from numpy import genfromtxt, sort
# pydfnworks Modules
from pydfnworks.dfnGen.meshing import mesh_dfn_helper as mh
from pydfnworks.dfnGen.meshing import lagrit_scripts_poisson_disc as lagrit
from pydfnworks.dfnGen.meshing import run_meshing as run_mesh
from pydfnworks.dfnGen.meshing.poisson_disc.poisson_functions import single_fracture_poisson, dump_poisson_params


[docs]def mesh_network(self, prune=False, uniform_mesh=False, production_mode=True, coarse_factor=8, slope=0.1, min_dist=1, max_dist=40, concurrent_samples=10, grid_size=10, visual_mode=None, well_flag=False): ''' Mesh fracture network using LaGriT Parameters ---------- self : object DFN Class prune : bool If prune is False, mesh entire network. If prune is True, mesh only fractures in self.prune_file uniform_mesh : bool If true, mesh is uniform resolution. If False, mesh is spatially variable production_mode : bool If True, all working files while meshing are cleaned up. If False, then working files will not be deleted visual_mode : None If the user wants to run in a different meshing mode from what is in params.txt, set visual_mode = True/False on command line to override meshing mode coarse_factor: float Maximum resolution of the mesh. Given as a factor of h slope : float slope of variable coarsening resolution. min_dist : float Range of constant min-distance around an intersection (in units of h). max_dist : float Range over which the min-distance between nodes increases (in units of h) concurrent_samples : int number of new candidates sampled around an accepted node at a time. grid_size : float side length of the occupancy grid is given by H/occupancy_factor well_flag : bool If well flag is true, higher resolution around the points in Returns ------- None Notes ------ 1. For uniform resolution mesh, set slope = 0 2. All fractures in self.prune_file must intersect at least 1 other fracture ''' print('=' * 80) print("Meshing DFN using LaGriT : Starting") print('=' * 80) if uniform_mesh: slope = 0 # Setting slope = 0, results in a uniform mesh if prune: if self.prune_file == "": error = "ERROR!! User requested pruning in meshing but \ did not provide file of fractures to keep.\nExiting program.\n" sys.stderr.write(error) sys.exit(1) mh.create_mesh_links(self.path) num_poly, h, params_visual_mode, dudded_points, domain = mh.parse_params_file( ) if visual_mode == None: visual_mode = params_visual_mode if visual_mode: print("\n--> Running in Visual Mode\n") print( f"Loading list of fractures to remain in network from {self.prune_file}" ) fracture_list = sort(genfromtxt(self.prune_file).astype(int)) print(fracture_list) if not visual_mode: lagrit.edit_intersection_files(num_poly, fracture_list, self.path) num_poly = len(fracture_list) else: num_poly, h, params_visual_mode, dudded_points, domain = mh.parse_params_file( ) if visual_mode == None: visual_mode = params_visual_mode fracture_list = range(1, num_poly + 1) # if number of fractures is greater than number of CPUS, # only use num_poly CPUs. This change is only made here, so ncpus # is still used in PFLOTRAN ncpu = min(self.ncpu, num_poly) print('=' * 80) if visual_mode: print("\n--> Running in Visual Mode\n") else: print("\n--> Running in Full Meshing Mode\n") print('=' * 80) lagrit.create_parameter_mlgi_file(fracture_list, h, slope=slope) if visual_mode: lagrit.create_lagrit_scripts_reduced_mesh(fracture_list) else: # Check for well points well. if well_flag: if not os.path.isfile("well_points.dat"): error = "ERROR!!! Well flag is set to True in DFN.mesh_network(), but file 'well_points.dat' cannot be found.\nPlease run DFN.find_well_intersection_points() for each well prior to meshing\nOr set well_flag = False\nExiting Program\n" sys.stderr.write(error) sys.exit(1) dump_poisson_params(h, coarse_factor, slope, min_dist, max_dist, concurrent_samples, grid_size, well_flag) lagrit.create_lagrit_scripts_poisson(fracture_list) ##### FOR SERIAL DEBUG ###### # for f in fracture_list: # run_mesh.mesh_fracture(f, visual_mode, len(fracture_list)) # exit() print('=' * 80) failure = run_mesh.mesh_fractures_header(fracture_list, ncpu, visual_mode, h) if failure: mh.cleanup_dir() error = "One or more fractures failed to mesh properly.\nExiting Program\n" sys.stderr.write(error) sys.exit(1) n_jobs = lagrit.create_merge_poly_files(ncpu, num_poly, fracture_list, h, visual_mode, domain, self.flow_solver) run_mesh.merge_the_meshes(num_poly, ncpu, n_jobs, visual_mode) if (not visual_mode and not prune): if not mh.check_dudded_points(dudded_points): mh.cleanup_dir() error = "ERROR!!! Incorrect Number of dudded points.\nExiting Program\n" sys.stderr.write(error) sys.exit(1) if production_mode: mh.cleanup_dir() if not visual_mode: lagrit.define_zones() if prune: mh.clean_up_files_after_prune(self) mh.output_meshing_report(self.local_jobname, visual_mode) print('=' * 80) print("Meshing DFN using LaGriT : Complete") print('=' * 80)