/*

Description: Basic class for fields in 2D and 3D; interface to xml-header
             
Author:      Raimundo Sierra
             www.rsierra.com

Copyright:   Copyright (c) 2000 Raimundo Sierra. All rights reserved.
LICENSE:     This program 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.

             This program 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 this program; if not, write to the Free Software
             Foundation, Inc., 675 Mass Ave, Cambridge, MA 02139, USA.


Institution: Surgical Planning Laboratory
             Department of Radiology
             Brigham and Women's Hospital
             Harvard Medical School
             MA 02115
             USA

Date:        11.2000 - 3.2001

Modifications:
<Date>   <Init>    <Version>    <Description>

*/



#ifndef _basefield
#define _basefield 1


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

#include <util/PlatformUtils.hpp>
#include <util/XMLString.hpp>
#include <util/TranscodingException.hpp>
#include <dom/DOM_DOMException.hpp>
#include <parsers/DOMParser.hpp>
#include <dom/DOM.hpp>
#include "DOMTreeErrorReporter.hpp"

#include <util/XMLUniDefs.hpp>
#include <framework/XMLFormatter.hpp>
#include <fstream.h>

#include "rsfunctions.h"

extern "C"{
#include "memfuns.h"
#include "fileops.h"
}  // end extern "C"

//#include <time.h> // for writing results
extern const int MAXSTRINGLENGTH;

class basefield{

 private:
  float readfloat(DOM_Node& node);         // read numerical values from node in xml file; return -1 if no value present
  int   readstring(DOM_Node& node, char* mystring);// read string from node in xml file; return -1 if no value present

                                           // read attribute as string from node in xml file; return -1 if no value present
                                           // pre:  mystring is the name of the attribute to get value
                                           // post: mystring is the value of the atttribute;
  int   readattribute(DOM_Node& node, char* mystring);

  void  readfile(DOM_Node& node);          // read the location of the datafile from node in xml file (could be removed)

  void  readdata(DOM_Node& node);          // read the xml file and extract the data wanted;
                                           //  start here to extract more/new data from an xml-file
                                           //  or when changing DTD

  void  readmanualy();                     // read ALL values from console
  void  readmanualy(int& value);           // read value from console, exit if entered -1
  void  readmanualy(float& value);         // dito
  void  readmanualy(char* value);          // dito

  void  assert_values();                   // check if all values to write XMLHeader are present
                                           //  if not, ask for values

 protected:
  int   _dimx, _dimy, _dimz;               // the dimensions of the field
  float _deltax, _deltay, _deltaz;         // the distance between voxels = voxelsize

  char *_datafile;                         // pointer to the datafile
  char *_orientation;                      // orientation of the field: axial, coronal, saggital
  char *_sourcefile;                       // location of source to derive tensorfile
  char *_originalfile;                     // location of the original data

  // baby specific data:
  int  _gestationalAge;                    // 
  int  _mrNumber;
  int  _studyNumber;
  int  _seriesNumber;
  char *_date;
  
 public:
  basefield();                             // Constructor
  virtual ~basefield();                    // Destructor

                                           // do everything needed to call readdata, should not need
  void read_XMLHeader( const char xmlFile[]);//  any editing when changing DTD

  void write_XMLHeader(const char xmlFile[]); // write a xml-header file at location xmlFile

  void setNumbers(const int age, const int patient_id, const int studyNr, const int seriesNumber);
  void setDate(const char* date);
  void setOrig(const char* orig);
  void setOrientation(const char orientation);

                                           // set voxelsize for field
  void setDelta(const float deltax, const float deltay, const float deltaz);
                                           // get voxelsize for field
  void getDelta(float& deltax, float& deltay, float& deltaz);
                                           // get dimension for field
  void getDimension(int& dimx, int& dimy, int& dimz);

  char * getPath(char * path);             // get the path to the data without any extension
  char * getSource(char * path);
  char * getOriginal(char * path);
  char * getDate(char * date);
  char * getOrientation(char * orientation);
  void getNumbers(int& Age, int& ID, int& Study, int& SerieNR);

  void getProperties(basefield &b_field);  // get all the properties from b_field into this field

                                           // check boundaries for offset and windowsize
                                           // and reset them if necessary.
                                           // used for display purposes:
                                           // Plane rotates the window depending on windowsize
                                           // plane[3] = 2: Image is in xy-plane
                                           //          = 1: Image is in xz-plane
                                           //          = 0: Image is in yz-plane
                                           // in each case plane[0] and plane[1] 
                                           // are the xy dimensions in the image coordinate system
                                           // plane[2] the number of images 
  void check_boundaries(int offset[3], int windowsize[3], int plane[4]=NULL) const; 

  short*          read_pic(short *image,          char path_file[], int offset=0);
  unsigned short* read_pic(unsigned short *image, char path_file[], int offset=0);

};

// ---------------------------------------------------------------------------
//  ostream << DOMString
//
//  Stream out a DOM string. Doing this requires that we first transcode
//  to char * form in the default code page for the system
// ---------------------------------------------------------------------------
ostream& operator<< (ostream& target, const DOMString& s);
// ---------------------------------------------------------------------------
//  ostream << DOM_Node   
//
//  Stream out a DOM node, and, recursively, all of its children. This
//  function is the heart of writing a DOM tree out as XML source. Give it
//  a document node and it will do the whole thing.
// ---------------------------------------------------------------------------
ostream& operator<<(ostream& target, DOM_Node& toWrite);
XMLFormatter& operator<< (XMLFormatter& strm, const DOMString& s);

#endif
