Source code for fluidfoam.openfoamsimu

"""Class to load all data saved at timeStep of an openFoam simulation
=====================================================================

.. autoclass:: OpenFoamSimu

.. automethod:: OpenFoamSimu.keys

.. automethod:: OpenFoamSimu.readopenfoam

"""

import os, sys
import subprocess
import numpy as np
from fluidfoam import readmesh, readfield, OpenFoamFile

class Error(Exception):
    pass

class DirectorySimuError(Error):
    def __init__(self, simu):
        super(DirectorySimuError,self).__init__(
                "No directory found for simulation named {}".format(simu))

[docs]class OpenFoamSimu(object): """ Class to load all data saved at timeStep of an openFoam simulation Args: path: str, reference path where simulations are stored.\n You may want to provide path if all your simulations are located inside path and subfolders of path. You can do it by modifying in the __init__ path='/path/to/the/simulations/'\n simu: str, name of the simu that has to be loaded.\n If simu=None, it will lists all existing simulation names in path and ask you to choose.\n timeStep: str, timeStep to load. If None, load the last time step\n structured: bool, true if the mesh is structured\n dataToLoad: list of str, list containing the name of the varaibles to read and load. If None, read and load all saved variables. """ def __init__(self, path=None, simu=None, timeStep=None, structured=False, dataToLoad=None, precision=10, order='F'): if path == None and simu == None: # If nothing if given, consider the current directory as the # simulation to load self.directory = os.getcwd()+'/' self.simu = os.getcwd().split('/')[-1] elif simu == None: # If only path is provided, consider all subfolders as possible # simulations to load self.directory = self._choose_simulation(path) self.simu = self.directory.split("/")[-2] else: # If path and simu are provided, consider the given directory # as the simulation to load self.simu = simu if path.endswith('/') is False: path += '/' self.directory = path + simu if self.directory.endswith('/') is False: self.directory += '/' self.readmesh(timeStep=timeStep, structured=structured, precision=precision, order=order) self.readopenfoam(timeStep=timeStep, structured=structured, dataToLoad=dataToLoad, precision=precision, order=order) def readmesh(self, timeStep=None, structured=False, precision=10, order='F'): if timeStep is None: dir_list = os.listdir(self.directory) time_list = [] for directory in dir_list: try: float(directory) time_list.append(directory) except: pass time_list.sort(key=float) timeStep = time_list[-1] elif type(timeStep) is int: #timeStep should be in a str format timeStep = str(timeStep) self.timeStep = timeStep # Check if cell center position is written in the output directory try: field = OpenFoamFile(path=self.directory, time_name=self.timeStep, name='C', structured=False, precision=precision, order=order) values = field.values shape = (3, values.size // 3) values = np.reshape(values, shape, order=order) if structured and not field.uniform: try: values[0:3, :] = values[0:3, self.ind] shape = (3,) + tuple(self.shape) values = np.reshape(values, shape, order=order) except: print("Variable {} could not be loaded".format(var)) self.variables.remove(var) X, Y, Z = values[0], values[1], values[2] except FileNotFoundError: X, Y, Z = readmesh(self.directory, structured=structured, precision=precision, order=order) self.x = X self.y = Y self.z = Z if structured: nx = np.unique(X).size ny = np.unique(Y).size nz = np.unique(Z).size self.ind = np.array(range(nx*ny*nz)) self.shape = (nx, ny, nz)
[docs] def readopenfoam(self, timeStep=None, structured=False, dataToLoad=None, precision=10, order='F'): """ Reading SedFoam results Load the last time step saved of the simulation Args: timeStep : str or int, timeStep to load. If None, load the last time step\n structured : bool, true if the mesh is structured """ if timeStep is None: dir_list = os.listdir(self.directory) time_list = [] for directory in dir_list: try: float(directory) time_list.append(directory) except: pass time_list.sort(key=float) timeStep = time_list[-1] elif type(timeStep) is int: #timeStep should be in a str format timeStep = str(timeStep) self.timeStep = timeStep #List all variables saved at the required time step removing potential #directory that cannot be loaded if dataToLoad is None: self.variables = [] basepath = self.directory+self.timeStep+'/' for fname in os.listdir(basepath): path = os.path.join(basepath, fname) if os.path.isdir(path): # skip directories continue else: self.variables.append(fname) #Remove C, Cx, Cy and Cz if present var_to_remove = ['C', 'Cx', 'Cy', 'Cz'] for var in var_to_remove: if var in self.variables: self.variables.remove(var) else: self.variables = dataToLoad for var in self.variables: #Load all variables and assign them as a variable of the object field = OpenFoamFile(path=self.directory, time_name=self.timeStep, name = var, structured=False, precision=precision, order=order) values = field.values if field.type_data == "scalar": if structured and not field.uniform: try: values = np.reshape(values[self.ind], self.shape, order=order) except: print("Variable {} could not be loaded".format(var)) self.variables.remove(var) continue elif field.type_data == "vector": shape = (3, values.size // 3) values = np.reshape(values, shape, order=order) if structured and not field.uniform: try: values[0:3, :] = values[0:3, self.ind] shape = (3,) + tuple(self.shape) values = np.reshape(values, shape, order=order) except: print("Variable {} could not be loaded".format(var)) self.variables.remove(var) continue elif field.type_data == "symmtensor": shape = (6, values.size // 6) values = np.reshape(values, shape, order=order) if structured and not field.uniform: try: values[0:6, :] = values[0:6, self.ind] shape = (6,) + tuple(self.shape) values = np.reshape(values, shape, order=order) except: print("Variable {} could not be loaded".format(var)) self.variables.remove(var) continue elif field.type_data == "tensor": shape = (9, values.size // 9) values = np.reshape(values, shape, order=order) if structured and not field.uniform: try: values[0:9, :] = values[0:9, self.ind] shape = (9,) + tuple(self.shape) values = np.reshape(values, shape, order=order) except: print("Variable {} could not be loaded".format(var)) self.variables.remove(var) continue self.__setattr__(var.replace('.', '_'), values)
[docs] def keys(self): """ Print the name of all variables loaded from simulation results """ print("Loaded available variables are :") print(self.variables)
def _choose_simulation(self, path): """ Make a list of all directories located in path containing a simulation. Ask the user which simulation to load Args: path : str, reference path where simulations are stored. """ directories = [] subDirectories = [x[0] for x in os.walk(path)] for f in subDirectories: #A directory is detected to be a simulation if it contains a 0_org/ folder if f + "/constant" in subDirectories: directories.append(f) # If no directories found if len(directories) == 0: raise DirectorySimuError(path) for i in range(len(directories)): print("{} : {}".format(i, directories[i])) chosenSimulation = -1 while type(chosenSimulation) is not int or ( chosenSimulation < 0 or chosenSimulation > len(directories) - 1): chosenSimulation = int( input( "Please, choose one simulation ! (integer between {} and {})".format( 0, len(directories) - 1)) ) directory = directories[chosenSimulation] return directory + "/" def _find_directory(self, path, simu): """ Look for the directory of simu in all the sub directories of path. If several directories are found, the program asks which directory is the good one. Args: path : str, reference path where simulations are stored. simu : str, name of the simu that has to be loaded. If None, it will lists all existing simulation names in path and ask you to choose """ directories = [] subDirectories = [x[0] for x in os.walk(path)] for f in subDirectories: if f.endswith(simu): directories.append(f) # If no directories found if len(directories) == 0: raise DirectorySimuError(simu) # If several directories found, ask for the one wanted elif len(directories) > 1: print("The following simulations has been found :") for i in range(len(directories)): print("{} : {}".format(i, directories[i])) chosenSimulation = -1 while type(chosenSimulation) is not int or ( chosenSimulation < 0 or chosenSimulation > len(directories) - 1): chosenSimulation = int(input( "Please, choose one simulation ! (integer between {} and {})".format( 0, len(directories) - 1) ) ) directory = directories[chosenSimulation] else: directory = directories[0] return directory + "/"
if __name__ == "__main__": simu = "box" timeStep = "4" for d in dirs: rep = os.path.join(os.path.dirname(__file__), "../output_samples") mySimu = OpenFoamSimu(path=rep, simu=simu, timeStep=timeStep, structured=True) mySimu.keys() mySimu.U