// This may look like C code, but it is really -*- C++ -*-
// RTSS --- Railway Total System Simulator
// (c) TAKAGI Ryo (at Kogakuin University)
// RS_XmlReader.hh --- class RS_XmlReader and related classes
// -----
// ChangeLog:
// 2009. 7. 10
//  File created.
// -----



#ifndef RS_XmlReader_HH
#define RS_XmlReader_HH

#include <cstdlib>
#include <string>
#include <map>
#include <iostream>
#include "RS_Object.hh"
#include "tinyxml.h"

using std :: map ;
using std :: string ;



/**************************************************************************
 * string getClassString ( const TiXmlNode * _n_in ) : Non-member function
 *  to find the class string.
 * string getNameString ( const TiXmlNode * _n_in ) : Non-member function
 *  to find the name string.
 * _n_in : tag containing attribute "class".
 **************************************************************************/
string getClassString ( TiXmlNode const * ) ;
string getNameString ( TiXmlNode const * ) ;


/************************************************************************
 * class RS_XmlReader
 * ----
 * This class reads XML-format data input files and create objects.
 * このクラスは，XML形式の入力ファイルを読み取り，オブジェクトを生成する。
 ************************************************************************/
class RS_XmlReader
  : public virtual RS_Object ,
    public map < string , RS_ObjectContainer * >
{
  // Information on current files.
  bool has_open_document ;
  string current_document_file_descriptor ;
  string current_drive ;
  string current_directory ;
  TiXmlDocument * curdoc ;
  TiXmlNode const * curnode ;
  TiXmlNode const * dtag ;

  // Subfunctions of processElement() member function.
  bool processCreateTag () ;

  explicit RS_XmlReader ( RS_XmlReader & ) ;

public :
  // Constructor.
  explicit RS_XmlReader ()
    : map < string , RS_ObjectContainer * > () , has_open_document ( false ) ,
      current_document_file_descriptor ( "" ) , current_drive ( "" ) ,
      current_directory ( "" ) , curdoc ( 0 ) , curnode ( 0 ) , dtag ( 0 ) {}
  
  /**********************************************************************
   * bool openXmlDocument ( const string & filedcr ,
   *  const string & curdrive , const string & curdir )
   * Opens an XML file and locate the first tag to be processed.
   * Returns true if successful.
   **********************************************************************/
  bool openXmlDocument
  ( string const & , string const & , string const & ) ;

  /**********************************************************************
   * bool hasNextElement ()
   * Locate next unprocessed tag. Returns true if there is one and the
   * operation successful. If no unprocessed tag is found, close the
   * current document.
   **********************************************************************/
  bool hasNextElement () ;

  /**********************************************************************
   * bool processElement ()
   * Process the current element. Returns true if successful.
   **********************************************************************/
  bool processElement () ;
} ;


#endif	// RS_XmlReader_HH
