package mosaiccreator;

import java.io.File;
import java.io.BufferedReader;
import java.util.Hashtable;
import java.io.FileReader;
import javax.swing.JLabel;
import javax.swing.JProgressBar;
import javax.swing.JFileChooser;

/**
 * <p>Title: Mosiac Opener</p>
 * <p>Description: this opens a .mosaic file into memory </p>
 * @author Lance Finfrock
 * @version 1.0
 */
public class MosaicOpener implements Runnable{

  private JProgressBar progressBar;
  private JLabel fileReadingIn;
  private MainWindow returnClass;

  /**
   * set to false to kill the process
   */
  public boolean isAlive;

  public MosaicOpener(JProgressBar progressbar, JLabel progressbarLabel, MainWindow mainwindow){
    this.progressBar = progressbar;
    this.fileReadingIn = progressbarLabel;
    this.returnClass = mainwindow;
    this.isAlive = true;
    Thread local  = new Thread(this);
    local.setPriority(Thread.MIN_PRIORITY);
    local.start();
  }

  public void run() {

    openMosaicFile();
    fileReadingIn.setText(" ");
    this.progressBar.setValue(0);
    this.progressBar.setVisible(false);
    returnClass.StoreMosaic();
  }
  /**
   * opens a .mosaic file
   * allows the user to find the file on there directory
   * read the file into memory and return back to the main Window
   */
  public void openMosaicFile(){

    JFileChooser fc = new JFileChooser();

    //only allow folders and .mosaic files to be seen
    fc.addChoosableFileFilter(new MosaicFilter());
    fc.setAcceptAllFileFilterUsed(false);

    //show the mosaci icon
    fc.setFileView(new MosaicFileView());

    //Show the file browser
    int returnVal = fc.showDialog(returnClass, "Open");

    //if the user has choosen a .mosaic file
    if (returnVal == JFileChooser.APPROVE_OPTION) {

      //get the file choosen
      File file = fc.getSelectedFile();

      //make sure it ends with .mosaic
      if (file.getName().endsWith(".mosaic")){

        try {

          //display to the user what is going on
          this.progressBar.setVisible(true);
          fileReadingIn.setText("Reading in File");

          Hashtable PixelsReadin = new Hashtable();

          //create a reader for the .mosaic file
          BufferedReader inData1 = new BufferedReader(new FileReader(file.getPath()));


          int DivionsWide = Integer.parseInt(inData1.readLine());
          int DivionsHigh = Integer.parseInt(inData1.readLine());

          String[] packetInfo = inData1.readLine().split(";");

          //read in the information for the original image
          PicPixels original = new PicPixels(packetInfo[0], Integer.parseInt(packetInfo[1]), Integer.parseInt(packetInfo[2]));

          //create the storage stop for the mosaic pieces
          PicPixels[] subPiecesPixels = new PicPixels[DivionsWide * DivionsHigh];


          //read in the mosaic pieces
          for(int i = 0;i < subPiecesPixels.length;i++){

            //read in the next line and break it on the ";"
            packetInfo = inData1.readLine().split(";");

            //show the user the progress
            progressBar.setValue((int)((((double)i)/subPiecesPixels.length) * 100));

            //the user has stoped the algorithm
            if(!this.isAlive) {
              MainWindow.currentMosaic = null;
              return ;
            }

            //if this image has already been read in the get that image
            //this is done for speed
            if(PixelsReadin.containsKey(packetInfo[0])){
              subPiecesPixels[i] = subPiecesPixels[((Integer)PixelsReadin.get(packetInfo[0])).intValue()];
            }
            else{//the image has not been read in

              //create the picPixels for the image
              subPiecesPixels[i] = new PicPixels(packetInfo[0],
                                                 Integer.parseInt(packetInfo[1]),
                                                 Integer.parseInt(packetInfo[2]));

              //add it to the hash table so that it will not have to be read in again
              PixelsReadin.put(packetInfo[0],new Integer(i));

            }
          }

          //create the mosaic
          MainWindow.currentMosaic = new Mosaic(subPiecesPixels, original, DivionsWide, DivionsHigh);

          //close the file
          inData1.close();

        }
        catch (Exception ex) {
          System.err.println(ex + "error reading in Mosaic");
        }
      }
    }
  }

}
