/*
 * ADAPT2D : a software for automatic mesh adaptation in 2D
 *
 * AUTHOR : Manuel J. Castro Diaz(e-mail:castro@gamba.cie.uma.es)
 * ADAPTED FOR FREEFEM : Prud'homme Christophe (e-mail:prudhomm@ann.jussieu.fr) 
 *
 * this code is public domain
 * 
 * You may copy freely these files and use it for    
 * teaching or research. These or part of these may   
 * not be sold or used for a commercial purpose without
 * our consent
 * 
 * Any problems should be reported to the AUTHOR
 * at the following address : castro@gamba.cie.uma.es
 */


#include <front_t0.hxx>
   
/*    
________________________________________________________________________
                       
                         SUBRRUTINA TESTEO      

    Testea si se puden ir uniendo trozos de frontera para formar una
    curva cerrada. Si los puede unir los unira en un sentido y otro
    segun pueda. El resultado final se una lista (Frontera_T0)
    cuyos elementos seran a su vez una lista de aristas, estas ordenadas
    y de tal manera que forman curvas. El numero de elementos de la
    lista (Frontera_T0) nos da el numero de componentes conexas
    de la frontera.
    
    Entrada: Una lista desordenada de aristas...
    Salida:  Las aristas ordenadas formando curvas. 
*/
    void Frontera_T0::testeo() {
          FraristaT0_link* aux,*aux1,*sig;
          aux=begin;
          while(aux) {
            aux1=aux->suc;
            while (aux1) {
              if ((*aux)<(*aux1)) {   
                   sig=aux1;
                   aux1=aux1->suc;
                   enlaza(aux,sig,1);
                   delete sig;
              }
              else {
                   if ((*aux1)<(*aux)) {
                      sig=aux1;
                      aux1=aux1->suc;
                      enlaza (aux,sig,-1);
                      delete sig;     
                   }
                   else aux1=aux1->suc;
              }
            }
            aux=aux->suc;
          }
   }

/*  --------------------------------------------------------------------

                       SUBRRUTINA D_FRONTERA

   Proposito:  Dado un punto y la Frontera de un dominio, busco la
   ---------   arista y por tanto, el elemento mas proximo al punto
               dado. Calcularemos tambien el proyectado sobre la arista.

   Entrada:    pt= Punto dado.
   -------     - Frontera apuntada por this.
               dista=distancia inicial, si no se conoce
                     poner infinito.
   Salida:     proyec= proyectado sobre la frontera.
   ------      aret=  arista mas cercana.
               trian= elemento que contine la arista.

*/
  Scalar Frontera_T0::d_frontera(R2 pt, R2& proyec,\
         Arista_T0& arete, Triangulo_T0& triangle,const Scalar& dista) {

         FraristaT0_link* aux1;
         AristaT0_list* comp_conex;
         AristaT0_link* aux;
         Arista_T0* aret;
         Scalar d0,dist=dista;
         R2 pr_pt(0,0);
         aux1=begin;

         while (aux1) {
           comp_conex=aux1->Aretelist;
           aux=comp_conex->principio();
           while(aux) {
             aret=aux->a;
             d0=d_arete(*aret,pt,pr_pt);
             if (d0<dist) {
                 dist=d0;
                 arete=*aret;
                 triangle=*(aret->tr);
                 proyec=pr_pt;
             }
             aux=aux->sig();
           }
           aux1=aux1->sig();
         }
         return dist;
    }


    void Frontera_T0::write (ostream& os) {
        int num=0,i=0;
        FraristaT0_link* aux;
        num=this->num_elem();
        os <<endl<<"Numero de curvas de la frontera:"<<num<<endl;
        aux=begin;
        while (aux) {
          i++;
          os <<aux<<" Curva:"<<i<<" constituida por las Aristas"<<endl;
          os <<(*(aux->Aretelist))<<endl;
          aux=aux->suc;
        }
     }

ostream& operator<<(ostream& os, Frontera_T0& fl)
{
  fl.write (os); return os;
}
