Logo Search packages:      
Sourcecode: ecs version File versions  Download package

ecs_champ_def.c

/*============================================================================
 *  Definitions des fonctions
 *   associees a la structure `ecs_champ_t' decrivant un champ
 *   et propres aux champs principaux de type "definition"
 *============================================================================*/

/*
  This file is part of the Code_Saturne Preprocessor, element of the
  Code_Saturne CFD tool.

  Copyright (C) 1999-2007 EDF S.A., France

  contact: saturne-support@edf.fr

  The Code_Saturne Preprocessor is free software; you can redistribute it
  and/or modify it under the terms of the GNU General Public License
  as published by the Free Software Foundation; either version 2 of
  the License, or (at your option) any later version.

  The Code_Saturne Preprocessor is distributed in the hope that it will be
  useful, but WITHOUT ANY WARRANTY; without even the implied warranty
  of MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE.  See the
  GNU General Public License for more details.

  You should have received a copy of the GNU General Public License
  along with the Code_Saturne Preprocessor; if not, write to the
  Free Software Foundation, Inc.,
  51 Franklin St, Fifth Floor,
  Boston, MA  02110-1301  USA
*/


/*============================================================================
 *                                 Visibilite
 *============================================================================*/

/*----------------------------------------------------------------------------
 *  Fichiers `include' librairie standard C ou BFT
 *----------------------------------------------------------------------------*/

#include <assert.h>
#include <string.h> /* strlen() */

#include <bft_mem.h>
#include <bft_printf.h>


/*----------------------------------------------------------------------------
 *  Fichiers `include' visibles du  paquetage global "Utilitaire"
 *----------------------------------------------------------------------------*/

#include "ecs_chaine_glob.h"
#include "ecs_chrono.h"
#include "ecs_elt_typ_liste.h"
#include "ecs_param_rc_glob.h"
#include "ecs_param_perio_glob.h"
#include "ecs_def.h"
#include "ecs_tab.h"


/*----------------------------------------------------------------------------
 *  Fichiers `include' visibles des paquetages visibles
 *----------------------------------------------------------------------------*/

#include "ecs_vec_int.h"
#include "ecs_vec_int_tri.h"
#include "ecs_vec_real.h"
#include "ecs_vec_real_tri.h"
#include "ecs_vec_def.h"
#include "ecs_vec_def_rc.h"
#include "ecs_vec_def_perio.h"


/*----------------------------------------------------------------------------
 *  Fichiers `include' visibles du  paquetage courant
 *----------------------------------------------------------------------------*/

#include "ecs_champ_vec_int.h"
#include "ecs_champ_vec_real.h"
#include "ecs_champ.h"


/*----------------------------------------------------------------------------
 *  Fichier  `include' du  paquetage courant associe au fichier courant
 *----------------------------------------------------------------------------*/

#include "ecs_champ_def.h"


/*----------------------------------------------------------------------------
 *  Fichiers `include' prives   du  paquetage courant
 *----------------------------------------------------------------------------*/

#include "ecs_champ_priv.h"


/*============================================================================
 *                       Macros globales au fichier
 *============================================================================*/

/* Longueur maximale du nom d'un type d'élément (+1 pour le `\0' !) */
#define ECS_LOC_LNG_MAX_NOM_TYP    11


/*============================================================================
 *                       Prototypes de fonctions privées
 *============================================================================*/


/*============================================================================
 *                             Fonctions publiques
 *============================================================================*/

/*----------------------------------------------------------------------------
 *  Fonction qui réalise le tri des types géométriques
 *  La fonction affiche le nombre d'éléments par type géométrique
 *----------------------------------------------------------------------------*/

ecs_tab_int_t ecs_champ_def__trie_typ
(
 ecs_champ_t * this_champ_def,
 int           dim_elt
)
{

  size_t       ielt ;
  size_t       nbr_elt ;
  size_t       nbr_som ;

  ecs_tab_int_t   tab_typ_geo_ord ;
  ecs_tab_int_t   tab_typ_geo ;
  ecs_tab_int_t   vect_renum ;

  ecs_elt_typ_t   typ_geo ;

  const ecs_elt_typ_t  *typ_geo_base ;

  const int lng_imp = ECS_LNG_AFF_STR - ECS_LOC_LNG_MAX_NOM_TYP ;


  /*xxxxxxxxxxxxxxxxxxxxxxxxxxx Instructions xxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxx*/


  assert(this_champ_def != NULL) ;

  vect_renum.nbr = 0    ;
  vect_renum.val = NULL ;

  nbr_elt = this_champ_def->nbr_elt ;

  if (nbr_elt == 0)
    return vect_renum ;


  /* Détermination de base du type d'élément "classique" */

  assert(dim_elt >=1 && dim_elt <= 3) ;

  typ_geo_base = ecs_glob_typ_elt[dim_elt - 1] ;


  /* Si tous les éléments sont de même type, rien à faire */
  /*------------------------------------------------------*/

  if (this_champ_def->pos_tab == NULL) {

    if (this_champ_def->pos_pas < 9)
      typ_geo = typ_geo_base[this_champ_def->pos_pas] ;
    else if (dim_elt == 2)
      typ_geo = ECS_ELT_TYP_FAC_POLY ;
    else if (dim_elt == 3)
      typ_geo = ECS_ELT_TYP_CEL_POLY ;
    else
      typ_geo = ECS_ELT_TYP_NUL ;

    bft_printf("  %-*s%*.*s : %*lu\n",
               lng_imp, _("Number of elements"),
               ECS_LOC_LNG_MAX_NOM_TYP, ECS_LOC_LNG_MAX_NOM_TYP,
               ecs_fic_elt_typ_liste_c[typ_geo].nom,
               ECS_LNG_AFF_ENT, (unsigned long)nbr_elt) ;

  }


  /* Si tous les éléments ne sont pas de même type */
  /*-----------------------------------------------*/

  else {

    /* Construction d'un tableau temporaire de type géométrique */

    tab_typ_geo.nbr = nbr_elt ;
    BFT_MALLOC(tab_typ_geo.val, tab_typ_geo.nbr, ecs_int_t) ;

    for (ielt = 0 ; ielt < nbr_elt ; ielt++) {

      nbr_som =   this_champ_def->pos_tab[ielt + 1]
                - this_champ_def->pos_tab[ielt] ;

      if (nbr_som < 9)
        tab_typ_geo.val[ielt] = typ_geo_base[nbr_som] ;

      else if (dim_elt == 2)
        tab_typ_geo.val[ielt] = ECS_ELT_TYP_FAC_POLY ;

      else if (dim_elt == 3)
        tab_typ_geo.val[ielt] = ECS_ELT_TYP_CEL_POLY ;

      else
        tab_typ_geo.val[ielt] = ECS_ELT_TYP_NUL ;

    }


    /* On regarde si les types géométriques ne sont pas deja ordonnés */

    ielt = 1 ;
    while (ielt < nbr_elt                                     &&
           tab_typ_geo.val[ielt] >= tab_typ_geo.val[ielt - 1]   )
      ielt++ ;

    if (ielt < nbr_elt) {

      /* Les types géométriques ne sont pas ordonnés */
      /* On ordonne les types géométriques */

      vect_renum.nbr = nbr_elt ;
      BFT_MALLOC(vect_renum.val, nbr_elt, ecs_int_t) ;


      tab_typ_geo_ord = ecs_tab_int__trie_et_renvoie(tab_typ_geo,
                                                     vect_renum) ;

      /*
        `vect_renum' prend pour indice les indices nouveaux, et ses valeurs
        contiennent les indices anciens correspondants
        On inverse le contenu de `vect_renum' :
        à chaque indice ancien, `vect_renum' donne la valeur du nouvel indice
      */

      ecs_tab_int__inverse(&vect_renum) ;

      BFT_FREE(tab_typ_geo.val) ;

      tab_typ_geo.val = tab_typ_geo_ord.val ;

      tab_typ_geo_ord.nbr = 0 ;
      tab_typ_geo_ord.val = NULL ;

    }


    /* Message d'information sur la composition des éléments du maillage */

    {
      ecs_int_t val_typ_ref ;
      size_t    nbr_val_typ_geo ;

      size_t    cpt_ielt = 0 ;

      while (cpt_ielt < nbr_elt) {

        val_typ_ref = tab_typ_geo.val[cpt_ielt] ;

        /* On compte le nombre d'éléments ayant le même type géométrique */

        nbr_val_typ_geo = 0 ;

        for (ielt = cpt_ielt ;
             ielt < nbr_elt && tab_typ_geo.val[ielt] == val_typ_ref ; ielt++)
          nbr_val_typ_geo++ ;

        bft_printf("  %-*s%*.*s : %*lu\n",
                   lng_imp, _("Number of elements"),
                   ECS_LOC_LNG_MAX_NOM_TYP, ECS_LOC_LNG_MAX_NOM_TYP,
                   ecs_fic_elt_typ_liste_c[val_typ_ref].nom,
                   ECS_LNG_AFF_ENT, (unsigned long)nbr_val_typ_geo) ;

        cpt_ielt += nbr_val_typ_geo ;

      }
    }


    /* Le tableau de type géométrique n'est plus nécessaire */

    tab_typ_geo.nbr = 0 ;
    BFT_FREE(tab_typ_geo.val) ;

  }


  /* Renvoi du vecteur de renumérotation */
  /*-------------------------------------*/

  return vect_renum ;

}


/*----------------------------------------------------------------------------
 *  Fonction qui construit
 *   les définitions des faces par décomposition des champs des cellules
 *----------------------------------------------------------------------------*/

void ecs_champ_def__decompose_cel
(
 ecs_champ_t *vect_champ_fac[],
 ecs_champ_t *champ_def_cel
)
{

  ecs_vec_int_t *vec_def_cel ;
  ecs_vec_int_t *vec_def_fac ;
  ecs_vec_int_t *vec_cel_def_fac ;

  size_t        nbr_fac ;


  /*xxxxxxxxxxxxxxxxxxxxxxxxxxx Instructions xxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxx*/


  /* Construction, pour les cellules,                             */
  /*  des vecteurs `ecs_vec_int_t' associés aux champs principaux */
  /*--------------------------------------------------------------*/

  vec_def_cel     = ecs_champ__initialise_vec_int(champ_def_cel) ;


  ecs_vec_def__decompose_cel(&vec_def_fac,
                             &vec_cel_def_fac,
                             vec_def_cel) ;


  ecs_vec_int__detruit(vec_def_cel) ;


  ecs_champ__transfere_vec_int(champ_def_cel,
                               vec_cel_def_fac) ;


  nbr_fac = ecs_vec_int__ret_pos_nbr(vec_def_fac) - 1 ;

  vect_champ_fac[ECS_CHAMP_DEF]
    = ecs_champ__init_avec_vec_int(vec_def_fac,
                                   ECS_CHAMP_NOM_DEFINIT) ;

  vect_champ_fac[ECS_CHAMP_DEF]->statut_e  = ECS_CHAMP_STATUT_INDEFINI ;

}


/*----------------------------------------------------------------------------
 *  Fonction qui construit
 *   les définitions des arêtes par décomposition des champs des faces
 *----------------------------------------------------------------------------*/

void ecs_champ_def__decompose_fac
(
 ecs_champ_t *vect_champ_are[],
 ecs_champ_t *champ_def_fac
)
{

  ecs_vec_int_t *vec_def_fac ;
  ecs_vec_int_t *vec_def_are ;
  ecs_vec_int_t *vec_fac_def_are ;

  size_t        nbr_are ;


  /*xxxxxxxxxxxxxxxxxxxxxxxxxxx Instructions xxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxx*/


  /* Construction, pour les elements,                         */
  /*  des vecteurs `ecs_vec_int_t' associes aux champs principaux */
  /*----------------------------------------------------------*/

  vec_def_fac     = ecs_champ__initialise_vec_int(champ_def_fac) ;


  ecs_vec_def__decompose_fac(&vec_def_are,
                             &vec_fac_def_are,
                             vec_def_fac) ;


  ecs_vec_int__detruit(vec_def_fac) ;


  ecs_champ__transfere_vec_int(champ_def_fac,
                               vec_fac_def_are) ;


  nbr_are = ecs_vec_int__ret_pos_nbr(vec_def_are) - 1 ;

  vect_champ_are[ECS_CHAMP_DEF]
    = ecs_champ__init_avec_vec_int(vec_def_are,
                                   ECS_CHAMP_NOM_DEFINIT) ;

  vect_champ_are[ECS_CHAMP_DEF]->statut_e  = ECS_CHAMP_STATUT_INDEFINI ;

}


/*----------------------------------------------------------------------------
 *  Fonction qui realise la fusion des definitions des elements
 *----------------------------------------------------------------------------*/

ecs_tab_int_t ecs_champ_def__int_fusionne
(
 ecs_champ_t   * this_champ_def, /* <-> Reference sur champ des definitions   */
 size_t        * nbr_elt_cpct,
 ecs_tab_int_t * signe_elt       /* <-- Signe des elts apres tri de leur def. */
)
{

  ecs_vec_int_t * vec_def ;      /* Vecteur des definitions des elements */
  ecs_tab_int_t   vect_transf ;  /* Vecteur de transformation */


  /*xxxxxxxxxxxxxxxxxxxxxxxxxxx Instructions xxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxx*/


  vec_def = ecs_champ__initialise_vec_int(this_champ_def) ;


  /* Fusion des definitions des elements sur la liste initiale  */
  /*------------------------------------------------------------*/

  vect_transf = ecs_vec_def__fusionne(&vec_def,
                                      signe_elt) ;


  /* Affectation de la nouvelle liste compactee */
  /*--------------------------------------------*/

  *nbr_elt_cpct = ecs_vec_int__ret_pos_nbr(vec_def) - 1 ;


  ecs_champ__transfere_vec_int(this_champ_def,
                               vec_def) ;


  /* Renvoi du vecteur de transformation */
  /*-------------------------------------*/

  return vect_transf ;

}


/*----------------------------------------------------------------------------
 *  Fonction qui realise la fusion des definitions des elements
 *----------------------------------------------------------------------------*/

ecs_tab_int_t ecs_champ_def__real_fusionne
(
 ecs_champ_t * this_champ_def, /* <-> Reference sur le champ des definitions */
 size_t      * nbr_elt_cpct
)
{

  ecs_vec_real_t * vec_def ;      /* Vecteur des definitions des elements */

  ecs_tab_int_t    vect_transf ;  /* Vecteur de transformation */


  /*xxxxxxxxxxxxxxxxxxxxxxxxxxx Instructions xxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxx*/


  vec_def = ecs_champ__initialise_vec_real(this_champ_def) ;


  /* Fusion des definitions des elements sur la liste initiale  */
  /*------------------------------------------------------------*/

  vect_transf = ecs_vec_real_def__fusionne(&vec_def) ;


  /* Affectation de la nouvelle liste compactee */
  /*--------------------------------------------*/

  *nbr_elt_cpct = ecs_vec_real__ret_pos_nbr(vec_def) - 1 ;

  ecs_champ__transfere_vec_real(this_champ_def,
                                vec_def) ;


  /* Renvoi du vecteur de transformation */
  /*-------------------------------------*/

  return vect_transf ;

}


/*----------------------------------------------------------------------------
 *  Fonction qui construit la liste des cellules attachées à une liste
 *  de faces fournie en argument.
 *----------------------------------------------------------------------------*/

ecs_tab_int_t ecs_champ_def__liste_cel_fac
(
 const ecs_int_t            nbr_fac,
       ecs_champ_t   *const champ_def_cel,
 const ecs_tab_int_t        liste_fac
)
{
  ecs_tab_int_t   liste_cel ;
  ecs_vec_int_t * vec_def_cel ;

  /*xxxxxxxxxxxxxxxxxxxxxxxxxxx Instructions xxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxx*/

  assert(champ_def_cel != NULL) ;


  vec_def_cel = ecs_champ__initialise_vec_int(champ_def_cel) ;


  liste_cel = ecs_vec_def__liste_cel_fac(nbr_fac,
                                         vec_def_cel,
                                         liste_fac) ;

  ecs_champ__libere_vec_int(champ_def_cel,
                            vec_def_cel) ;

  return liste_cel ;

}


/*----------------------------------------------------------------------------
 *  Fonction qui construit la table de connectivite "faces -> sommets"
 *----------------------------------------------------------------------------*/

ecs_champ_t * ecs_champ_def__cree_fac_som
(
 ecs_champ_t       *const champ_def_fac,
 ecs_champ_t       *const champ_def_are
)
{

  ecs_champ_t   * champ_connect_fac_som ;

  ecs_vec_int_t * vec_connect_fac_som ;
  ecs_vec_int_t * vec_def_fac ;
  ecs_vec_int_t * vec_def_are ;


  /*xxxxxxxxxxxxxxxxxxxxxxxxxxx Instructions xxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxx*/


  assert(champ_def_fac != NULL) ;
  assert(champ_def_are != NULL) ;


  vec_def_fac = ecs_champ__initialise_vec_int(champ_def_fac) ;
  vec_def_are = ecs_champ__initialise_vec_int(champ_def_are) ;

  vec_connect_fac_som = ecs_vec_def__cree_fac_som(vec_def_fac,
                                                  vec_def_are) ;

  ecs_champ__libere_vec_int(champ_def_fac,
                            vec_def_fac) ;

  ecs_champ__libere_vec_int(champ_def_are,
                            vec_def_are) ;

  champ_connect_fac_som = ecs_champ__init_avec_vec_int(vec_connect_fac_som,
                                                       ECS_CHAMP_NOM_DEFINIT) ;

  champ_connect_fac_som->statut_e = ECS_CHAMP_STATUT_INDEFINI ;


  return champ_connect_fac_som ;


}


/*----------------------------------------------------------------------------
 *  Fonction realisant le decoupage des faces polygonales en triangles
 *
 *  Le maillage doit être en connectivité nodale.
 *----------------------------------------------------------------------------*/

ecs_champ_t * ecs_champ_def__dec_poly_tria
(
 ecs_champ_t        *      vect_champ_fac[],
 ecs_champ_t        *const champ_def_som
)
{

  size_t           nbr_fac ;
  size_t           nbr_fac_new ;
  size_t           nbr_fac_val_new ;

  size_t           fac_nbr_som_max ;

  ecs_vec_int_t  * vec_def_fac_new ;
  ecs_vec_int_t  * vec_def_fac ;
  ecs_vec_real_t * vec_def_som ;
  ecs_vec_int_t  * vec_def_fac_dec ;

  ecs_champ_t    * champ_def_fac_dec ;


  /*xxxxxxxxxxxxxxxxxxxxxxxxxxx Instructions xxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxx*/


  assert(vect_champ_fac != NULL) ;
  assert(vect_champ_fac[ECS_CHAMP_DEF] != NULL) ;

  vec_def_fac = ecs_champ__initialise_vec_int(vect_champ_fac[ECS_CHAMP_DEF]) ;
  vec_def_som = ecs_champ__initialise_vec_real(champ_def_som) ;

  nbr_fac = ecs_vec_int__ret_pos_nbr(vec_def_fac) - 1 ;


  /* Comptage pour allocations */

  ecs_vec_def__cpt_poly_tria(vec_def_fac,
                             &fac_nbr_som_max,
                             &nbr_fac_new,
                             &nbr_fac_val_new) ;


  /* Allocation et initialisation                                             */
  /*  pour les nouvelles (et anciennes) faces definies en fonction des aretes */
  /*  des vecteurs `ecs_vec_int_t' associes aux champs principaux             */

  vec_def_fac_new
    = ecs_vec_int__alloue(nbr_fac_new + 1,
                          nbr_fac_val_new);


  /* Redefinition des faces en triangles (en fonctions des aretes) */
  /* Definition des nouvelles aretes issues du decoupage           */
  /* Renvoi de la definition                                       */
  /*  des anciennes faces en fonction des nouvelles (triangles)    */


  vec_def_fac_dec = ecs_vec_def__dec_poly_tria(vec_def_fac_new,
                                               vec_def_fac,
                                               vec_def_som,
                                               fac_nbr_som_max,
                                               nbr_fac_new) ;


  ecs_champ__libere_vec_real(champ_def_som,
                             vec_def_som) ;


  /*------------------------------------------------*/
  /* Construction du champ contenant la definition  */
  /*  des anciennes faces en fonction des nouvelles */
  /*------------------------------------------------*/


  champ_def_fac_dec = ecs_champ__init_avec_vec_int(vec_def_fac_dec,
                                                   ECS_CHAMP_NOM_DEFINIT) ;

  champ_def_fac_dec->statut_e = ECS_CHAMP_STATUT_INDEFINI ;


  /*--------------------------------------------------------*/
  /* Construction du vecteur des champs des nouvelles faces */
  /*--------------------------------------------------------*/


  /* Construction du champ contenant la definition */
  /*  des nouvelles faces en fonction des sommets  */
  /*-----------------------------------------------*/

  ecs_vec_int__detruit(vec_def_fac) ;

  nbr_fac_new = ecs_vec_int__ret_pos_nbr(vec_def_fac_new) - 1 ;

  ecs_champ__transfere_vec_int(vect_champ_fac[ECS_CHAMP_DEF],
                               vec_def_fac_new) ;



  return champ_def_fac_dec ;

}


/*----------------------------------------------------------------------------
 *  Fonction qui construit un tableau de booleens conforme a une liste
 *   de sous-elements
 *  Un sous-element est a `ECS_TRUE'
 *   s'il intervient dans la definition des elements
 *----------------------------------------------------------------------------*/

void ecs_champ_def__cree_masque
(
 ecs_tab_bool_t        bool_sselt_select,
 ecs_champ_t    *const champ_def_elt
)
{

  ecs_vec_int_t * vec_def_elt ;


  /*xxxxxxxxxxxxxxxxxxxxxxxxxxx Instructions xxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxx*/


  vec_def_elt = ecs_champ__initialise_vec_int(champ_def_elt) ;


  ecs_vec_def__cree_masque(bool_sselt_select,
                           vec_def_elt) ;


  ecs_champ__libere_vec_int(champ_def_elt,
                            vec_def_elt) ;


}


/*----------------------------------------------------------------------------
 *  Fonction qui renvoie le nombre de faces de type "polygone"
 *  (basée sur la définition de faces par plus de 4 arêtes)
 *----------------------------------------------------------------------------*/

size_t  ecs_champ_def__nbr_fac_poly
(
 ecs_champ_t  *const champ_def_fac
)
{

  ecs_vec_int_t  * vec_def_fac ;

  size_t           nbr_fac_poly ;


  /*xxxxxxxxxxxxxxxxxxxxxxxxxxx Instructions xxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxx*/


  vec_def_fac = ecs_champ__initialise_vec_int(champ_def_fac) ;


  nbr_fac_poly = ecs_vec_def__nbr_fac_poly(vec_def_fac) ;


  ecs_champ__libere_vec_int(champ_def_fac,
                            vec_def_fac) ;


  return nbr_fac_poly ;

}


/*----------------------------------------------------------------------------
 *  Suppression des sommets ne participant pas à la connectivité
 *   (renvoie le champ de renumérotation des sommets, ou NULL si aucune
 *   renumérotation n'a été nécessaire).
 *----------------------------------------------------------------------------*/

ecs_champ_t * ecs_champ_def__nettoie_nodal
(
 ecs_champ_t       *const champ_def_som,
 ecs_champ_t       *const champ_def_are,
 ecs_champ_t       *const champ_def_fac,
 ecs_champ_t       *const champ_def_cel
)
{

  ecs_champ_t     * champ_som_old_new ;

  ecs_vec_int_t   * vec_som_old_new ;

  ecs_vec_real_t  * vec_def_som = NULL ;
  ecs_vec_int_t   * vec_def_fac = NULL ;
  ecs_vec_int_t   * vec_def_are = NULL ;
  ecs_vec_int_t   * vec_def_cel = NULL ;


  /*xxxxxxxxxxxxxxxxxxxxxxxxxxx Instructions xxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxx*/


  if (champ_def_som == NULL)
    return NULL ;


  vec_def_som = ecs_champ__initialise_vec_real(champ_def_som) ;

  if (champ_def_are != NULL)
    vec_def_are = ecs_champ__initialise_vec_int(champ_def_are) ;

  if (champ_def_fac != NULL)
    vec_def_fac = ecs_champ__initialise_vec_int(champ_def_fac) ;

  if (champ_def_cel != NULL)
    vec_def_cel = ecs_champ__initialise_vec_int(champ_def_cel) ;


  vec_som_old_new = ecs_vec_def__nettoie_nodal(vec_def_som,
                                               vec_def_are,
                                               vec_def_fac,
                                               vec_def_cel) ;


  if (vec_def_are != NULL)
    ecs_champ__libere_vec_int(champ_def_are,
                              vec_def_are) ;

  if (vec_def_fac != NULL)
    ecs_champ__libere_vec_int(champ_def_fac,
                              vec_def_fac) ;

  if (vec_def_cel != NULL)
    ecs_champ__libere_vec_int(champ_def_cel,
                              vec_def_cel) ;


  /* Opérations nécessaires selon si l'on a effectué un compactage ou pas */

  if (vec_som_old_new != NULL) {

    ecs_champ__transfere_vec_real(champ_def_som,
                                  vec_def_som) ;


    champ_som_old_new = ecs_champ__init_avec_vec_int(vec_som_old_new,
                                                     NULL) ;

  }
  else {

    ecs_champ__libere_vec_real(champ_def_som,
                               vec_def_som) ;

    champ_som_old_new = NULL ;

  }


  return champ_som_old_new ;

}


/*----------------------------------------------------------------------------
 *  Correction si nécessaire de l'orientation des éléments en
 *   connectivité nodale.
 *----------------------------------------------------------------------------*/

void ecs_champ_def__orient_nodal
(
       ecs_champ_t    *const champ_def_som,   /*  -> Définition des sommets   */
       ecs_champ_t    *const champ_def_fac,   /*  -> Définition des faces     */
       ecs_champ_t    *const champ_def_cel,   /*  -> Définition des cellules  */
       ecs_tab_int_t  *const liste_cel_err,   /* <-  Cels. erreur (option)    */
       ecs_tab_int_t  *const liste_cel_cor,   /* <-  Cels. correct. (option)  */
 const ecs_bool_t            correc_orient    /*  -> Correction ou non        */
)
{

  ecs_vec_real_t  * vec_def_som = NULL ;
  ecs_vec_int_t   * vec_def_fac = NULL ;
  ecs_vec_int_t   * vec_def_cel = NULL ;


  /*xxxxxxxxxxxxxxxxxxxxxxxxxxx Instructions xxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxx*/


  if (champ_def_som == NULL)
    return ;


  vec_def_som = ecs_champ__initialise_vec_real(champ_def_som) ;

  if (champ_def_fac != NULL)
    vec_def_fac = ecs_champ__initialise_vec_int(champ_def_fac) ;

  if (champ_def_cel != NULL)
    vec_def_cel = ecs_champ__initialise_vec_int(champ_def_cel) ;


  ecs_vec_def__orient_nodal(vec_def_som,
                            vec_def_fac,
                            vec_def_cel,
                            liste_cel_err,
                            liste_cel_cor,
                            correc_orient) ;


  ecs_champ__libere_vec_real(champ_def_som,
                             vec_def_som) ;

  if (vec_def_fac != NULL)
    ecs_champ__libere_vec_int(champ_def_fac,
                              vec_def_fac) ;

  if (vec_def_cel != NULL)
    ecs_champ__libere_vec_int(champ_def_cel,
                              vec_def_cel) ;

}


/*----------------------------------------------------------------------------
 *  Fusion des sommets confondus d'après la longueur des arêtes.
 * La connectivité des arêtes est mise à jour.
 *----------------------------------------------------------------------------*/

void ecs_champ_def__nettoie_som_are
(
 ecs_champ_t       *const champ_def_som,
 ecs_champ_t       *const champ_def_are
)
{

  ecs_vec_int_t   * vec_som_old_new ;

  ecs_vec_real_t  * vec_def_som = NULL ;
  ecs_vec_int_t   * vec_def_are = NULL ;


  /*xxxxxxxxxxxxxxxxxxxxxxxxxxx Instructions xxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxx*/


  if (champ_def_som == NULL || champ_def_are == NULL)
    return ;


  vec_def_som = ecs_champ__initialise_vec_real(champ_def_som) ;
  vec_def_are = ecs_champ__initialise_vec_int(champ_def_are) ;


  vec_som_old_new = ecs_vec_def__nettoie_som_are(vec_def_som,
                                                 vec_def_are) ;


  if (vec_def_are != NULL)
    ecs_champ__libere_vec_int(champ_def_are,
                              vec_def_are) ;


  /* Opérations nécessaires selon si l'on a effectué un compactage ou pas */

  if (vec_som_old_new != NULL) {

    ecs_champ__transfere_vec_real(champ_def_som,
                                  vec_def_som) ;

    ecs_vec_int__detruit(vec_som_old_new) ;

  }

  else

    ecs_champ__libere_vec_real(champ_def_som,
                               vec_def_som) ;

}


/*----------------------------------------------------------------------------
 *  Fonction qui supprime les éventuelles arêtes dégénérées
 *----------------------------------------------------------------------------*/

ecs_champ_t * ecs_champ_def__nettoie_are
(
 ecs_champ_t       *const champ_def_are
)
{

  ecs_champ_t     * champ_are_old_new ;

  ecs_vec_int_t   * vec_are_old_new ;

  ecs_vec_int_t   * vec_def_are = NULL ;


  /*xxxxxxxxxxxxxxxxxxxxxxxxxxx Instructions xxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxx*/


  if (champ_def_are == NULL)
    return NULL ;


  vec_def_are = ecs_champ__initialise_vec_int(champ_def_are) ;


  vec_are_old_new = ecs_vec_def__nettoie_are(vec_def_are) ;


  /* Opérations nécessaires selon si l'on a effectué un compactage ou pas */

  if (vec_are_old_new != NULL) {

    ecs_champ__transfere_vec_int(champ_def_are,
                                 vec_def_are) ;

    champ_are_old_new = ecs_champ__init_avec_vec_int(vec_are_old_new,
                                                     NULL) ;

  }
  else {

    ecs_champ__libere_vec_int(champ_def_are,
                              vec_def_are) ;

    champ_are_old_new = NULL ;

  }


  return champ_are_old_new ;

}


/*----------------------------------------------------------------------------
 *  Fonction qui supprime les éventuelles faces dégénérées
 *----------------------------------------------------------------------------*/

ecs_champ_t * ecs_champ_def__nettoie_fac
(
 ecs_champ_t       *const champ_def_fac
)
{

  ecs_champ_t     * champ_fac_old_new ;

  ecs_vec_int_t   * vec_fac_old_new ;

  ecs_vec_int_t   * vec_def_fac = NULL ;


  /*xxxxxxxxxxxxxxxxxxxxxxxxxxx Instructions xxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxx*/


  if (champ_def_fac == NULL)
    return NULL ;


  vec_def_fac = ecs_champ__initialise_vec_int(champ_def_fac) ;


  vec_fac_old_new = ecs_vec_def__nettoie_fac(vec_def_fac) ;


  /* Opérations nécessaires selon si l'on a effectué un compactage ou pas */

  if (vec_fac_old_new != NULL) {

    ecs_champ__transfere_vec_int(champ_def_fac,
                                 vec_def_fac) ;

    champ_fac_old_new = ecs_champ__init_avec_vec_int(vec_fac_old_new,
                                                     NULL) ;

  }
  else {

    ecs_champ__libere_vec_int(champ_def_fac,
                              vec_def_fac) ;

    champ_fac_old_new = NULL ;

  }


  return champ_fac_old_new ;

}


/*----------------------------------------------------------------------------
 *  Fonction qui calcule les coordonnées minimales et maximales
 *----------------------------------------------------------------------------*/

void ecs_champ_def__calc_coo_ext
(
 ecs_champ_t   *const champ_som_def
)
{

  ecs_vec_real_t  * vec_real_som_def     ;


  /*xxxxxxxxxxxxxxxxxxxxxxxxxxx Instructions xxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxx*/


  vec_real_som_def = ecs_champ__initialise_vec_real(champ_som_def) ;

  ecs_vec_def__calc_coo_ext(vec_real_som_def) ;

  ecs_champ__libere_vec_real(champ_som_def    ,
                             vec_real_som_def  ) ;

}


/*----------------------------------------------------------------------------
 *  Fonction qui modifie les coordonnées du maillage
 *----------------------------------------------------------------------------*/

void ecs_champ_def__transf_coo
(
 ecs_champ_t   *const champ_som_def,
 const double         matrice[3][4]
)
{

  ecs_vec_real_t  * vec_real_som_def ;


  /*xxxxxxxxxxxxxxxxxxxxxxxxxxx Instructions xxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxx*/


  vec_real_som_def = ecs_champ__initialise_vec_real(champ_som_def) ;

  ecs_vec_def__transf_coo(vec_real_som_def,
                          matrice) ;

  ecs_champ__transfere_vec_real(champ_som_def,
                                vec_real_som_def) ;

}


/*----------------------------------------------------------------------------
 *  Fonction qui recolle les faces non conformes
 *
 *  Les listes des faces nouvelles ou modifiées sont construites (et allouées)
 *  ici ; les structures liste_fac_new et liste_fac_mod correspondantes sont
 *  donc vides en entrée ; idem pour liste_fac_err qui indiquera les indices
 *  des faces pour lesquelles le découpage en sous-faces a échoué
 *
 *  On prend en entrée soit une définition de type "visibilité" entre faces
 *  à recoller (par exemple une filiation), ou alors une simple liste de
 *  faces sélectionnées. L'un de vec_fac_vis et tab_fac_select doit donc
 *  être à NULL, et l'autre non.
 *----------------------------------------------------------------------------*/

void ecs_champ_def__recolle
(
       ecs_champ_t       *const champ_def_fac,
       ecs_champ_t       *const champ_def_are,
       ecs_champ_t       *const champ_def_som,
       ecs_champ_t     * *const champ_fac_old_new,
       ecs_champ_t     * *const champ_fac_perio,
       ecs_champ_t       *const champ_fac_vis,
       ecs_tab_int_t     *const tab_fac_de_bord_select,
       ecs_tab_int_t     *const liste_fac_new,
       ecs_tab_int_t     *const liste_fac_mod,
       ecs_tab_int_t     *const liste_fac_err,
 const ecs_param_rc_t           param_rc
)
{

  ecs_vec_int_t  * vec_def_fac ;
  ecs_vec_int_t  * vec_def_are ;
  ecs_vec_real_t * vec_def_som ;

  ecs_vec_int_t  * vec_fac_old_new ;
  ecs_vec_int_t  * vec_fac_vis ;

  ecs_vec_int_t  * vec_fac_perio ;
  ecs_vec_int_t  * vec_are_perio ;
  ecs_vec_int_t  * vec_som_perio ;

  /*xxxxxxxxxxxxxxxxxxxxxxxxxxx Instructions xxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxx*/


  assert(champ_def_fac != NULL) ;
  assert(champ_def_are != NULL) ;
  assert(champ_def_som != NULL) ;


  vec_def_fac = ecs_champ__initialise_vec_int(champ_def_fac) ;
  vec_def_are = ecs_champ__initialise_vec_int(champ_def_are) ;
  vec_def_som = ecs_champ__initialise_vec_real(champ_def_som) ;

  if (champ_fac_vis != NULL)
    vec_fac_vis = ecs_champ__initialise_vec_int(champ_fac_vis) ;
  else
    vec_fac_vis = NULL ;

  vec_fac_old_new = NULL ;

  vec_fac_perio = NULL ;
  vec_are_perio = NULL ;
  vec_som_perio = NULL ;


  ecs_vec_def__recolle(&vec_def_fac,
                       &vec_def_are,
                       &vec_def_som,
                       &vec_fac_old_new,
                       vec_fac_vis,
                       &vec_fac_perio,
                       &vec_are_perio,
                       &vec_som_perio,
                       tab_fac_de_bord_select,
                       liste_fac_new,
                       liste_fac_mod,
                       liste_fac_err,
                       param_rc) ;


  if (champ_fac_vis != NULL)
    ecs_champ__libere_vec_int(champ_fac_vis,
                              vec_fac_vis) ;

  ecs_champ__transfere_vec_int(champ_def_fac,
                               vec_def_fac) ;

  ecs_champ__transfere_vec_int(champ_def_are,
                               vec_def_are) ;

  ecs_champ__transfere_vec_real(champ_def_som,
                                vec_def_som) ;


  *champ_fac_old_new = ecs_champ__init_avec_vec_int(vec_fac_old_new,
                                                    NULL) ;


  /* On reference le champ de correspondance des faces periodiques */

  if (param_rc.param_perio != NULL) {

    char *nom_perio ;


    BFT_MALLOC(nom_perio, strlen(ECS_CHAMP_NOM_FAC_PERIO) + 5 + 1, char) ;

    sprintf(nom_perio, "%s %4d", ECS_CHAMP_NOM_FAC_PERIO,
            (param_rc.param_perio)->num_perio) ;

    *champ_fac_perio = ecs_champ__init_avec_vec_int(vec_fac_perio, nom_perio) ;

    (*champ_fac_perio)->statut_e = ECS_CHAMP_STATUT_REF_ELT ;

    BFT_FREE(nom_perio) ;

  }


}


/*----------------------------------------------------------------------------
 *  Fonction qui renvoie un tableau associant un type à chaque face, sous
 * forme de masque : 0 pour face isolée, 1 ou 2 pour face de bord (1 si
 * cellule avec cette face normale sortante, 2 si cellule avec cette face
 * normale entrante), 1+2 = 3 pour face interne, et 4 ou plus pour tous
 * les autres cas, correspondant à une erreur de connectivité (+4 pour faces
 * voyant au moins deux cellules avec face normale sortante, +8 pour faces
 * voyant au moins deux cellules avec face normale entrante).
 *
 *  Le type de chaque face pourra être modifié ultérieurement en fonction
 * des informations de périodicité.
 *----------------------------------------------------------------------------*/

ecs_tab_int_t ecs_champ_def__typ_fac_cel
(
 ecs_champ_t    *const champ_def_cel,
 ecs_champ_t    *const champ_def_fac
)
{

  size_t            nbr_fac ;
  ecs_vec_int_t   * vec_def_cel = NULL ;

  ecs_tab_int_t     typ_fac_cel ;


  /*xxxxxxxxxxxxxxxxxxxxxxxxxxx Instructions xxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxx*/


  typ_fac_cel.nbr = 0 ;
  typ_fac_cel.val = NULL ;

  if (champ_def_cel == NULL)
    return typ_fac_cel ;


  vec_def_cel = ecs_champ__initialise_vec_int(champ_def_cel) ;

  nbr_fac = ecs_champ__ret_pos_nbr(champ_def_fac) - 1 ;

  typ_fac_cel = ecs_vec_def__typ_fac_cel(vec_def_cel,
                                         nbr_fac) ;

  ecs_champ__libere_vec_int(champ_def_cel,
                            vec_def_cel) ;

  return typ_fac_cel ;

}


/*----------------------------------------------------------------------------
 *  Fonction qui renvoie un tableau associant un type à chaque face les
 * numéros des cellules définies par cette face (normale sortante,
 * puis normale entrante). On affecte une valeur 0 lorsqu'il n'y a pas de
 * cellule correspondante directe (la périodicité n'est donc pas prise en
 * compte à ce niveau).
 *
 * On suppose que la cohérence du maillage a déjà été véridifiée et
 * qu'aucune face n'appartient à plus d'une cellule par côté.
 *----------------------------------------------------------------------------*/

ecs_tab_int_t ecs_champ_def__fac_cel
(
 ecs_champ_t       *const champ_def_cel,
 ecs_champ_t       *const champ_def_fac
)
{

  size_t            nbr_fac ;
  ecs_vec_int_t   * vec_def_cel = NULL ;

  ecs_tab_int_t     fac_cel ;


  /*xxxxxxxxxxxxxxxxxxxxxxxxxxx Instructions xxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxx*/


  fac_cel.nbr = 0 ;
  fac_cel.val = NULL ;

  if (champ_def_cel == NULL)
    return fac_cel ;


  vec_def_cel = ecs_champ__initialise_vec_int(champ_def_cel) ;

  nbr_fac = ecs_champ__ret_pos_nbr(champ_def_fac) - 1 ;

  fac_cel = ecs_vec_def__fac_cel(vec_def_cel,
                                 nbr_fac) ;

  ecs_champ__libere_vec_int(champ_def_cel,
                            vec_def_cel) ;

  return fac_cel ;

}


/*----------------------------------------------------------------------------
 *  Fonction qui renvoie un tableau associant à chaque cellule un code
 * en fonction des erreurs de connectivité éventuelles associées à cette
 * cellule (0 si pas d'erreur, 1 si une des faces définissant cette cellule
 * s'appuie sur plusieurs cellules du même côté).
 *----------------------------------------------------------------------------*/

ecs_tab_int_t ecs_champ_def__err_cel_connect
(
       ecs_champ_t    *const champ_def_cel,
 const ecs_tab_int_t  *const typ_fac_cel
)
{

  ecs_vec_int_t   * vec_def_cel = NULL ;

  ecs_tab_int_t     typ_cell_connect ;


  /*xxxxxxxxxxxxxxxxxxxxxxxxxxx Instructions xxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxx*/


  typ_cell_connect.nbr = 0 ;
  typ_cell_connect.val = NULL ;

  if (champ_def_cel == NULL)
    return typ_cell_connect ;


  vec_def_cel = ecs_champ__initialise_vec_int(champ_def_cel) ;

  typ_cell_connect = ecs_vec_def__err_cel_connect(vec_def_cel,
                                                  typ_fac_cel) ;

  ecs_champ__libere_vec_int(champ_def_cel,
                            vec_def_cel) ;

  return typ_cell_connect ;

}


/*============================================================================
 *                              Fonctions privees
 *============================================================================*/

Generated by  Doxygen 1.6.0   Back to index