/***********************************************************************
*
* Projet    : DilibPro
* Module    : Sgml
* Fichier   : SgmlAtt.c
* Auteur    : Ducloy
* $Id: SgmlAtt.c,v 1.2 2005/06/22 13:17:15 parmentf Exp $
*
************************************************************************
*
* Copyright (c) 1994 CNRS/CRIN & INRIA Lorraine
* 
************************************************************************/

/*
   fonctions particulières aux listes d'attributs

*/

#include "SgmlNodePrivate.h"

#include <stdio.h>
#include <string.h>
#include <stdlib.h>

SgmlNode *SgmlAddLast();
SgmlNode *SgmlCreateAtt();
SgmlNode *SgmlCreateAttList();
void      SgmlFree();

/****************************************************************************** 
 *                              SgmlCreateAtt
 *
 * - Fonction qui crée une cellule de type SgmlNode spécifique à un attribut
 *
 * - Les paramètres : 
 *		- Id  : le nom de l'attribut
 *		- Val : la valeur de l'attribut
 *
 * - Valeur retournée : un pointeur sur la cellule
 *
 ******************************************************************************/

SgmlNode	*SgmlCreateAtt (char *Id, char *Val)
{
  SgmlNode	*CurAtt;

  CurAtt = SgmlCreateNode('A');
  SgmlAttId(CurAtt) = (char *)malloc( strlen(Id) + 1 );
  SgmlAttVal(CurAtt) = (char *)malloc( strlen(Val) + 1 );
  strcpy(SgmlAttId(CurAtt),Id);
  strcpy(SgmlAttVal(CurAtt),Val);
  SgmlNodeFormat(CurAtt)= SgmlNodeFormatAtt;

  return(CurAtt);

} /* end SgmlCreateAtt */



/****************************************************************************** 
 *                              SgmlCreateAttList
 *
 * - Fonction qui crée une cellule de type SgmlNode spécifique à une liste d'attributs
 *
 * - Valeur retournée : un pointeur sur la cellule
 *
 *
 *
 ******************************************************************************/
SgmlNode	*SgmlCreateAttList()
{
  SgmlNode	*CurLatt;

  CurLatt = SgmlCreateNode('L');

  return(CurLatt);
} /* end SgmlCreateAttList */



/*************************************************************************
*   SgmlGetAttById
*  retourne le premier attribut dont la valeur correspond au parametre
*
*
*****************************************************************************/
SgmlNode *SgmlGetAttById(SgmlNode *Mark, char *AttId)
{
    
    if ( !Mark )             return (NULL);
    {
    switch ( SgmlType(Mark) )
        {
         case 'M' : return (SgmlGetAttById (SgmlAttList(Mark),AttId));
                    
         case 'L' : return (SgmlGetAttById (SgmlFirst(Mark),AttId));
                    
         case 'A' : if (strcmp (AttId, SgmlAttId(Mark))==0) 
                         return (Mark);
                    else return(SgmlGetAttById (SgmlNext(Mark),AttId));
                    
         default  : return (NULL);
         
        }
    }
}


char *SgmlGetAttValById(SgmlNode *Mark, char *AttId)
{
   SgmlNode *Att;
   Att = SgmlGetAttById(Mark,AttId);
   if (Att) return (SgmlAttVal(Att));
   else return (NULL);
}

/*******************************************************************************
*                 SgmlAddAtt
*  fonction qui ajoute un SgmlNode attribut a un SgmlNode de type Mark
*
* Auteur : J. DUCLOY
*
********************************************************************************/
SgmlNode	*SgmlAddAtt (SgmlNode *Mark, char *Id, char *Val)
{
  SgmlNode  *CurAtt;
  SgmlNode  *CurLatt;

  CurAtt = SgmlCreateAtt(Id,Val);
  if  (SgmlAttList(Mark))
        {
         SgmlAddLast(SgmlAttList(Mark), CurAtt);
        }
  else
        {
         CurLatt=SgmlCreateAttList();
         SgmlAddLast(CurLatt, CurAtt);
         SgmlFather(CurLatt) = Mark;
         SgmlAttList(Mark) = CurLatt;
        }
  

  return(CurAtt);

} /* end SgmlAddAtt */


SgmlNode* SgmlSetAtt(SgmlNode *mark, char *attId, char *attVal)
{
  SgmlNode *att;
  int l2;
  if ((att=SgmlGetAttById(mark,attId)))
    {
      l2=strlen(attVal); 
      if(l2>strlen(SgmlAttVal(att)))
	 {
	   free(SgmlAttVal(att));
	   SgmlAttVal(att)=malloc(l2+1);
	 }
      strcpy(SgmlAttVal(att),attVal);
    }
  else SgmlAddAtt(mark,attId,attVal);
  return (mark);
}




/****************************************************************************

      SgmlNewAttList

*****************************************************************************/
SgmlNode *SgmlNewAttList (SgmlNode *mark, SgmlNode *attList)
{
  if (mark) 
    {
      if (SgmlAttList(mark)) SgmlFree(SgmlAttList(mark));
      if (attList)
	{
	  SgmlAttList(mark)=attList;
	  SgmlFather(attList)=mark;
	};
    }
  return (mark);
}

char *SgmlHasAtt(SgmlNode *n1, char *a1, char *v1)
{
  char *r1;
  char *v2;
  r1=NULL;
  if (n1&&((v2=SgmlGetAttValById(n1,a1))))
    {
      if (v1)
	{
	  if (strcmp(v1,v2)==0) r1=v2;
	}
      else r1=v2;
    }
  return r1;
}
