package PrintLabyrinth;
import java.io.*;

/**
 * class provides methods for generating a labyrinth XML file
 * for the tag names and the labyrinth symbols the classes
 * TagName and LabSymbols are used
 */

public class WriteLabToXML
{
  /** labyrinth field containing the labyrinth data */
  private LabyrinthField lab_field_;

  /** robot containing the robot data */
  private Robot robot_;


  public WriteLabToXML(LabyrinthField lab_field, Robot robot)
  {
    lab_field_ = lab_field;
    robot_ = robot;
  }

//------------------------------------------------------------------------------
/**
 * method transforms a string to an other one which can be used as a start tag
 * @param tag_name name of the tag
 * @return transformed string
 */
  protected String toStartTagString(String tag_name)
  {
    String tag_string = "<" + tag_name + ">";
    return tag_string;
  }

//------------------------------------------------------------------------------
/**
 * method transforms a string to an other one which can be used as a end tag
 * @param tag_name name of the tag
 * @return transformed string
 */
  protected String toEndTagString(String tag_name)
  {
    String tag_string = "</" + tag_name + ">\r\n";
    return tag_string;
  }

//------------------------------------------------------------------------------
/**
 * method writes the widht-element to the specified stream
 * @param out stream to use for writing
 * @exception IOException if out.write throws an Exception
 */
  public void writeWidth(OutputStreamWriter out)
    throws IOException
  {
    out.write(toStartTagString( TagName.WIDTH) + lab_field_.getNumCols() +
    toEndTagString(TagName.WIDTH));
  }

//------------------------------------------------------------------------------
/**
 * method writes the height-element to the specified stream
 * @param out stream to use for writing
 * @exception IOException if out.write throws an Exception
 */
  public void writeHeight(OutputStreamWriter out)
    throws IOException
  {
    out.write(toStartTagString(TagName.HEIGHT) + lab_field_.getNumRows()+
    toEndTagString(TagName.HEIGHT));
  }

//------------------------------------------------------------------------------
/**
 * method writes the dimension-element and all elements it contains to the specified stream
 * @param out stream to use for writing
 * @exception IOException if out.write throws an Exception
 */
  public void writeDimension(OutputStreamWriter out)
    throws IOException
  {
    out.write(toStartTagString(TagName.DIMENSION) + "\r\n");
    writeWidth(out);
    writeHeight(out);
    out.write(toEndTagString(TagName.DIMENSION));
  }

//------------------------------------------------------------------------------
/**
 * method writes a symbol-element to the specified stream
 * @param out stream to use for writing
 * @param tag_name name of the symbol-element
 * @param symbol symbol to write
 * @exception IOException if out.write throws an Exception
 */
  public void writeSymbol(OutputStreamWriter out, String tag_name, String symbol)
    throws IOException
  {
    out.write(toStartTagString(tag_name)+ symbol + toEndTagString(tag_name));
  }

//------------------------------------------------------------------------------
/**
 * method writes the startdirection-element to the specified stream
 * @param out stream to use for writing
 * @exception IOException if out.write throws an Exception
 */
  public void writeStartDirection(OutputStreamWriter out)
    throws IOException
  {
    out.write(toStartTagString(TagName.STARTDIRECTION)+ robot_.GetStartDirection() +
      toEndTagString(TagName.STARTDIRECTION));
  }

//------------------------------------------------------------------------------
/**
 * method writes the labyrinth-element with the ASCII representation
 * of the labyrinth field to the specified stream
 * @param out stream to use for writing
 * @exception IOException if out.write throws an Exception
 */
  public void writeLabyrinth(OutputStreamWriter out)
    throws IOException
  {
    try
    {
      out.write(toStartTagString(TagName.LABYRINTH) + "\r\n");
      for(int row_count=0 ; row_count< lab_field_.getNumRows(); row_count++)
      {
        for(int col_count = 0; col_count < lab_field_.getNumCols(); col_count++)
        {
          //if(((Cell)lab_field_.getElement(row_count, col_count)).isWall())
          if(lab_field_.isWall(row_count, col_count))
          {
            out.write(LabSymbols.WALLSYMBOL);
          }
          //else if(((Cell)lab_field_.getElement(row_count, col_count)).containsDiamond())
          else if(lab_field_.containsDiamond(row_count, col_count))
          {
            out.write(LabSymbols.DIAMONDSYMBOL);
          }
          //else if(((Cell)lab_field_.getElement(row_count, col_count)).isStartpoint())
          else if(lab_field_.isStartpoint(row_count, col_count))
          {
            out.write(LabSymbols.STARTSYMBOL);
          }
          //else if(((Cell)lab_field_.getElement(row_count, col_count)).isWay())
          else if(lab_field_.isWay(row_count, col_count))
          {
            out.write(LabSymbols.WAYSYMBOL);
          }
        }
        out.write("\r\n");
      }
      out.write(toEndTagString(TagName.LABYRINTH));
    }
    catch(IndexOutOfBoundsException ex)
    {
      System.out.println(ex.getMessage());
    }

  }

//------------------------------------------------------------------------------
/**
 * method writes the robotlabyrinth-element and all elements it contains to the specified stream
 * @param out stream to use for writing
 * @exception IOException if out.write throws an Exception
 */
  public void writeRobotLabyrinth(OutputStreamWriter out)
    throws IOException
  {
    out.write(toStartTagString(TagName.ROBOTLABYRINTH) + "\r\n");
    writeDimension(out);
    writeSymbol(out, TagName.STARTSYMBOL, "S");
    writeSymbol(out, TagName.WALLSYMBOL, "W");
    writeSymbol(out, TagName.DIAMONDSYMBOL, "D");
    writeSymbol(out, TagName.GALLERYSYMBOL, ".");
    writeSymbol(out, TagName.WORMSYMBOL, "~");
    writeStartDirection(out);
    writeLabyrinth(out);
    out.write(toEndTagString(TagName.ROBOTLABYRINTH) + "\r\n");
  }

//------------------------------------------------------------------------------
/**
 * method creates a XML file with the given filename and writes the header and
 * the whole labyrinth data in this file
 * @param file_name name of the XML file
 */
  public void writeXMLFile(String file_name)
  {
    try
    {
      OutputStream fout= new FileOutputStream(file_name);
      OutputStream bout= new BufferedOutputStream(fout);
      OutputStreamWriter out
       = new OutputStreamWriter(bout, "8859_1");
      out.write("<?xml version=\"1.0\" ");
      out.write("encoding=\"ISO-8859-1\"?>\r\n");
      writeRobotLabyrinth(out);
      out.flush();
      out.close();
    }
    catch(UnsupportedEncodingException e)
    {
      System.err.println(
        "This VM does not support the Latin-1 character set."
        );
    }
    catch (IOException e)
    {
      System.err.println(e.getMessage());
    }

  }
}
