tofu.plugins.ITER.Bolo.geom._core — tofu v1.1

# Source code for tofu.plugins.ITER.Bolo.geom._core

    # -*- coding: utf-8 -*-
    """
    Created on Wed Mar  5 10:42:24 2014

    @author: didiervezinet
    """

    import os
    import numpy as np
    import datetime as dtm
    import warnings

    # ToFu-specific
    import tofu.defaults as tfd
    import tofu.pathfile as tfpf
    import tofu.geom as tfg
    from ... import _path as _tfiter_path
    from ... import Ves as tfiterVes

    __author__ = "Didier Vezinet"
    __all__ = ["create_Apert","create_Detect","create_GDetect", "load"]

    Exp = 'ITER'

    SavePathObj = '/afs/ipp-garching.mpg.de/home/g/gav/ToFu_ITER/Objects_ITER/'
    SavePathInp = '/afs/ipp-garching.mpg.de/home/g/gav/ToFu_ITER/Inputs_ITER/'

    ############################################################################
    ############################################################################
    ############################################################################
    # --------- Objects creation -------
    ############################################################################

    def create_Apert(Name, Ves, Poly, shot=0, SavePathVes=SavePathObj, SavePathObj=SavePathObj, SavePathInp=SavePathInp, comments='#', skiprows=0, units='m', save=True):
        """
        Create a Apert object (i.e.: aperture) with specified Name from either a file (.dat,.txt,.csv) or directly from a (2,N) or (N,2) numpy array
        Object is created, Saved in SavePathObj and returned
        If an input file is specified and the file name does not include an absolute path, the path specified in SavePathInp is used

        Parameters
        ----------
        Name :          str
            Name of the object to be created
        Ves :           str / :class:`tofu.geom.Ves`
            Ves object to which the aperture is associated, a file name can also be used if the Ves object was previously Saved
        Poly :          str / np.ndarray
            Numpy array or input file name (fed to numpy.loadtxt) used to specify the polygon to be used (should be (2,N) or (N,2) for N points)
        shot :          int
            Shot number from which the provided geometry is valid (useful for geometry changes bewteen campaigns)
        SavePathVes :   None / str
            (optional) if Ves is a str (i.e.: file name) or a list (i.e.: list of strings contained in the file name), specifies the path at which the file is to be found
        SavePathObj :   None / str
            (optional) Absolute path where the created object will be saved
        SavePathInp :   None / str
            (optional) Absolute path where the input file is to be found
        comments :      str
            (optional) str specifying the flag for comments in the Poly file (if Poly is a file name), fed to numpy.loadtxt
        skiprows :      int
            (optional) number of rows to be skipped in the Poly file (if Poly is a file name), fed to numpy.loadtxt
        units :         str
            Flag indicating in which units the input polygon is provided (in ['m','cm','mm'])
        save :          bool
            (optional) Flag indicating whether the created object should be Saved
        Test :          bool
            Flag indicating whether the inputs should be tested for conformity

        Returns
        -------
        Apert :         :class:`tofu.geom.Apert`
            The created Apert object

        """
        if Test:
            assert type(Name) is str, "Arg Name must be a str !"
            assert type(Ves) in [tfg.Ves,str], "Ves must be specified (tfg.Ves or file name) !"
            assert type(Poly) in [str,list,np.ndarray], "Poly must be specified (np.ndarray or file name) !"
            assert type(shot) is int, "Arg shot must be a int !"
            assert all([ss is None or type(ss) is str for ss in [SavePathVes,SavePathInp,SavePathObj]]), "Args [SavePathInp,SavePathObj] must be str !"
            assert type(save) is bool, "Arg save must be a bool !"
            assert type(units) is str and units in ['m','cm','mm'], "Arg units must be in ['m','cm','mm'] !"

        # Get default path for loading inputs and saving object
        #SavePathObj, SavePathInp = _get_defaultsSavePathsdtime(SavePathObj=SavePathObj, SavePathInp=SavePathInp, Type='Object')
        if SavePathInp is None:
            SavePathInp = Root + '/tofu/plugins/'+_Exp+'/Bolo/geom/Inputs/'
        if SavePathObj is None:
            SavePathObj = Root + '/tofu/plugins/'+_Exp+'/Bolo/geom/Objects/'

        # Loading the Ves object
        if type(Ves) in [str.list]:
            Ves = tfiterVes.load(Name=Ves, SavePathObj=SavePathVes)

        # Get polygon and info
        Poly, addInfo = tfpf.get_PolyFromPolyFileObj(Poly, SavePathInp, units=units, comments=comments, skiprows=skiprows, shape0=3)

        # Create Apert object
        Apert = tfg.Apert(Name, Poly, Ves=Ves, Exp='ITER', Diag='Bolo', shot=shot, arrayorder='C', Clock=False, SavePath=SavePathObj)

        # Add info about input to Id
        for dd in addInfo.keys():
            Apert.Id._USRdict[dd] = addInfo[dd]

        if save:
            Apert.save()
        return Apert

    def create_Detect(Name, Ves, Poly, LApert, shot=0, SavePathVes=SavePathObj, SavePathObj=SavePathObj, SavePathInp=SavePathInp, comments='#', skiprows=0,
                      Cone_DRY=0.0025, Cone_DXTheta=np.pi/1024., Cone_DZ=0.0025, Cone_NPsi=20, Cone_Nk=60,
                      Synth_dX12=[0.005, 0.005], Synth_dX12Mode='abs', Synth_ds=0.005, Synth_dsMode='abs', Synth_Colis=True,
                      Calc=True, CalcEtend=True, CalcSpanImp=True, CalcCone=True, CalcPreComp=True, save=True, save_SynthDiag=False):
        """
        Create a :class:`tofu.geom.Detect` object (i.e.: detector) with specified Name from either a file (.dat,.txt,.csv) or directly from a (2,N) or (N,2) numpy array
        Object is created, optionally Saved in SavePathObj and returned
        If an input file is specified and the file name does not include an absolute path, the path specified in SavePathInp is used

        Parameters
        ----------
        Name :          str
            Name of the object to be created
        Ves :           :class:`tofu.geom.Ves` or str
            Ves object to which the aperture is associated, a file name can also be used if the Ves object was previously Saved
        Poly :          str or np.ndarray
            Numpy array or input file name (fed to numpy.loadtxt) used to specify the polygon to be used (should be (2,N) or (N,2) for N points)
        LApert :        list
            List of Apert objects to be associated to the detector
        SavePathVes :   None / str
            (optional) if Ves is a str (i.e.: file name) or a list (i.e.: list of strings contained in the file name), specifies the path at which the file is to be found
        SavePathObj :   str
            (optional) Absolute path where the created object will be Saved
        SavePathInp :   str
            (optional) Absolute path where the input file is to be found
        comments :      str
            (optional) str specifying the flag for comments in the Poly file (if Poly is a file name), fed to numpy.loadtxt
        skiprows :      int
            (optional) number of rows to be skipped in the Poly file (if Poly is a file name), fed to numpy.loadtxt
        save :          bool
            (optional) Flag indicating whether the created object should be Saved
        save_SynthDiag :    bool
            (optional) Flag indicating whether the pre-computed synthetic diagnostic mesh should also be saved (larger files) or whether it should be recomputed upon loading

        To compute the VOS, tofu tests all points inside a 3D grid to see if each point is visible from the detector through the apertures or not
        Cone_DR :        float
            Resolution of the grid in the R direction, in meters
        Cone_DTheta :    float
            Resolution of the grid in the toroidal direction, in radians
        Cone_DZ :        float
            Resolution of the grid in the Z direction, in meters

        In the particular case when the LOS of the detector lies entirely inside one poloidal cross-section (e.g.: tomography diagnostics),
        tofu also computes the integral in the toroidal direction of the solid angle on a regular mesh (for faster computation of the geometry assuming toroidaly invariant basis functions)
        This regular mesh is defined in 2D, by the distance between a mesh point and the detector (k) and by the poloidal angle between the LOS and the line going from the detector to the mesh point (psi)
        Cone_NPsi :      20
            Number of points of the regular mesh in psi direction (angle)
        Cone_Nk :        60
            Number of points of the regular mesh in k direction (distance)

        To compute synthetic signal faster for any simulated emissivity, tofu can pre-compute a 3D mesh of the VOS and store it, with the associates solid angles
        This 3D mesh is computed with respect to the LOS. One coordinate (s) is the distance along the LOS, the two others (1 and 2) are the distances in directions perpendicular to the LOS
        Synth_dX12 :      list
            Resolution of the mesh in the two directions perpendicular to the LOS
        Synth_dX12Mode :  str
            Flag indicating whether dX12 is an absolute value ('abs', in meters) or a fraction of the maximum local with of the VOS ('rel')
        Synth_ds :        float
            Resolution of the mesh in the direction parallel to the LOS
        Synth_dsMode :    str
            Flag indicating whether ds is an absolute value ('abs', in meters) or a fraction of the maximum local with of the VOS ('rel')
        Synth_Colis :     bool
            Flag indicating whether the collision detection should be activated

        Returns
        -------
        Detect :           TFG.Detect
            The created TFG.Detect object

        """
        if Test:
            assert type(Name) is str, "Arg Name must be a str !"
            assert type(Ves) in [tfg.Ves,str], "Ves must be specified (tfg.Ves or file name) !"
            assert type(Poly) in [str,list,np.ndarray], "Poly must be specified (np.ndarray or file name) !"
            assert type(LApert) is list and all([type(ss) in [TFG.Apert,str] for ss in LApert]), "Arg LApert must be a list of apertures, specified by file name or directly TFG.Apert !"
            assert type(shot) is int, "Arg shot must be a int !"
            assert all([ss is None or type(ss) is str for ss in [SavePathVes,SavePathInp,SavePathObj]]), "Args [SavePathInp,SavePathObj] must be str !"
            assert type(save) is bool, "Arg save must be a bool !"
            assert type(units) is str and units in ['m','cm','mm'], "Arg units must be in ['m','cm','mm'] !"

        # Get default path for loading inputs and saving object
        #SavePathObj, SavePathInp = _get_defaultsSavePathsdtime(SavePathObj=SavePathObj, SavePathInp=SavePathInp, Type='Object')
        if SavePathInp is None:
            SavePathInp = Root + '/tofu/plugins/'+_Exp+'/Bolo/geom/Inputs/'
        if SavePathObj is None:
            SavePathObj = Root + '/tofu/plugins/'+_Exp+'/Bolo/geom/Objects/'

        # Loading the Ves object
        if type(Ves) in [str.list]:
            Ves = tfiterVes.load(Name=Ves, SavePathObj=SavePathVes)

        # Loading apertures
        for ii in range(0,len(LApert)):
            if type(LApert[ii]) is str:
                PathFileExt = tfpf._get_PathFileExt_FromName(LApert[ii], Path=SavePathObj, Lstr=['TFG_Apert','ITER','Bolo',LApert[ii],'.npz'])
                LApert[ii] = tfpf.Open(PathFileExt)

        # Get polygon and info
        Poly, addInfo = tfpf.get_PolyFromPolyFileObj(Poly, SavePathInp, units=units, comments=comments, skiprows=skiprows, shape0=3)

        # Create Detect
        Detect = TFG.Detect(Id, Poly, Ves=Ves, LApert=LApert, Exp='ITER', Diag='Bolo', shot=shot,
                            Cone_DRY=Cone_DRY, Cone_DXTheta=Cone_DXTheta, Cone_DZ=Cone_DZ, Cone_NPsi=Cone_NPsi, Cone_Nk=Cone_Nk,
                            Calc=True, CalcEtend=True, CalcSpanImp=True, CalcCone=CalcCone, CalcPreComp=False, SavePath=SavePathObj)

        # Now compute the pre-computed mesh for synthetic signal, with default or specified parameters
        if CalcPreComp:
            LPar = {'dX12':Synth_dX12, 'dX12Mode':Synth_dX12Mode, 'ds':Synth_ds, 'dsMode':Synth_dsMode, 'Colis':Synth_Colis}
            Detect.set_SigPrecomp(**params)

        if save:
            Detect.save()
        return Detect

    def create_GDetect(Name, LDetect, SavePathObj=SavePathObj, save=True, save_SynthDiag=False):
        """
        Create a :class:`tofu.geom.GDetect` object (i.e.: group of detectors, or camera) with specified Name from a list of Detect objects
        Object is created, optionally Saved in SavePathObj and returned

        Parameters
        ----------
        Name :          str
            Name of the object to be created
        LDetect :       list
            List of already-created Detect objects
        SavePathObj :   str
            (optional) Absolute path where the created object will be Saved
        save :          bool
            (optional) Flag indicating whether the created object should be Saved
        save_SynthDiag :    bool
            (optional) Flag indicating whether the pre-computed synthetic diagnostic mesh should also be saved (larger files) or whether it should be recomputed upon loading

        Returns
        -------
        GD :            :class:`tofu.geom.GDetect`
            The created object

        """

        if SavePathObj is None:
            SavePathObj = shot=LDetect[0].Id.SavePath

        GD = tfg.GDetect(Name, LDetect, Exp='ITER', Diag='Bolo', shot=LDetect[0].Id.shot, SavePath=SavePathObj)
        if save:
            GD.save(SynthDiag=save_SynthDiag)
        return GD

    def load(Name, Cls='GDetect', SavePathObj=SavePathObj):
        """ Load the desired object, identified by name and saving path

        Searches in SavePathObj a ToFu object of the specified class (Cls) saved under the specified name (Name).
        If a single match is found, the object is loaded and returned, otherwise an error is raised

        Parameters
        ----------
        Name :      str
            Name of the object
        Cls :       str
            Class of the object, in ['Ves','Apert','Detect','GDetect']
        SavePathObj :   str
            Path under which the object is to be found

        """

        LD = os.listdir(SavePathObj)
        LD = [ff for ff in LD if all([ss in ff for ss in ['TFG_','ITER','Bolo',Cls,Name,'.npz']])]
        assert len(LD)==1, "Several or no matching file for "+Name+" of class "+Cls+" in "+SavePathObj

        obj = tfpf.open(SavePathObj+LD[0])
        return obj