/*
 * RowInfoMatcher.java
 *
 * Created on May 25, 2006, 12:52 PM
 *
 * To change this template, choose Tools | Template Manager
 * and open the template in the editor.
 */

package usda.weru.util.diff.listbuilders;

import de.schlichtherle.truezip.file.TFile;


import java.io.FileNotFoundException;
import java.util.ArrayList;
import java.util.List;
import javax.swing.JOptionPane;
import usda.weru.mcrew.CropObject;
import usda.weru.mcrew.ManageData;
import usda.weru.mcrew.OperationObject;
import usda.weru.soil.IFC;
import usda.weru.util.RunDirectory;
import usda.weru.util.WepsFileTypes;
import usda.weru.util.WepsMessage;
import usda.weru.util.WepsMessageDialog;
import usda.weru.util.WepsMessageLog;
import usda.weru.util.diff.*;
import usda.weru.weps.RunFileData;


/**
 *
 * @author Joseph Levin
 */
public class WepsFileListBuilder extends FileListBuilder{

	/**
	 *
	 */
	public static final int NORMAL = 1;

	/**
	 *
	 */
	public static final int RUN_DIR = 2;

	/**
	 *
	 */
	public static final int RUN = 3;

	/**
	 *
	 */
	public static final int PROJECT_DIR = 8;

	/**
	 *
	 */
	public static final int SOIL = 16;

	/**
	 *
	 */
	public static final int MANAGEMENT = 32;

	/**
	 *
	 */
	public static final int CROP = 64;

	/**
	 *
	 */
	public static final int OPERATION = 128;

	/**
	 *
	 */
	public static final int ROTATION = 256;

	/**
	 *
	 * @param engine
	 * @param a
	 * @param b
	 * @return
	 * @throws IncomparableObjectsException
	 */
	@Override
    public DiffNode buildList(DiffEngine engine, Object a, Object b) throws IncomparableObjectsException{
        test(TFile.class, a, b);
        return applyExtras(buildList(engine, (TFile) a,(TFile) b));        
    }

	/**
	 *
	 * @param engine
	 * @param fileA
	 * @param fileB
	 * @return
	 */
	@Override
    public DiffNode buildList (DiffEngine engine, TFile fileA, TFile fileB){                       
        if (typeOfFile(fileA) != NORMAL || typeOfFile(fileB) != NORMAL){
            Object first = objectFromFile(fileA);
            Object second = objectFromFile(fileB);
            DiffNode node = new DiffNode(first, second);
            node.setBuildFlag(true);
            return node;
        }
        else{
            return super.buildList(engine, fileA, fileB);
        }
        
        
    }
    
    public Object objectFromFile(TFile file)
    {
        int type = typeOfFile(file);
        switch(type)
        {
            case PROJECT_DIR:/*FALLTHROUGH*/
                //return new ProjectDirectory(file);
            case RUN_DIR:
                return new RunDirectory(file);
            case RUN:
                if(file.exists())
                {
                    RunFileData data = new RunFileData();
                    data.readRunFile(file);
                    return data;
                }
                else return null;
            case MANAGEMENT: /*FALLTHROUGH*/
            case ROTATION:
                if(file.exists())
                {
                    ManageData data = new ManageData();
                    data.readDataFile(file.getAbsolutePath());
                    ArrayList<String> messages = new ArrayList<String>();
                    if(data.checkAllConditions(messages) == ManageData.CHECK_FAILED)
                    {
                        messages.stream().forEach((message) -> {
                            DifferFrame.LOGGER.error(message);
                        });
                        JOptionPane.showMessageDialog(null, "Unable to read  management file:\n"
                            + file.getName(), "Diff", JOptionPane.ERROR_MESSAGE);
                        return null;
                    }
                    else return data;
                }
                else return null;
            case SOIL:
                IFC data = new IFC();
                try
                {
                    data.readIfc(file.getAbsolutePath());
                    return data;
                }
                catch(FileNotFoundException fail)
                {
                    fail.printStackTrace();
                    return null;
                }
            case CROP:
                CropObject crop = new CropObject();
                crop.readXMLFile(file.getAbsolutePath());
                return crop;
            case OPERATION:
                OperationObject operation = new OperationObject();
                operation.readXMLFile(file.getAbsolutePath());
                return operation;
            default:
                return file;
        }
    }

	/**
	 *
	 * @param file
	 * @return
	 */
	public static int typeOfFile(TFile file){
        if (file == null) return NORMAL;
        String fileName = file.getName();
        if (fileName.endsWith(RunFileData.RunSuffix)){
            //Run Directory
            return RUN_DIR;
            
        }
        else if(fileName.endsWith(".run")){
            //Run File
            return RUN;
        }
        else if(fileName.endsWith(RunFileData.ProjectSuffix)){
            //Project Directory
            return PROJECT_DIR;
        }
        else if(fileName.endsWith(".ifc")){
            //Soil File
            return SOIL;
        }
        else if(fileName.endsWith(".man")){
            //Management File
            return MANAGEMENT;
        }
        else if(WepsFileTypes.Rotation.accept(file)){
            //Rot File
            return ROTATION;
        }
        else if(fileName.endsWith(".oprn")){
            return OPERATION;
        }
        else if(fileName.endsWith(".crop")){
            return CROP;
        }
        else return NORMAL;
    }

	/**
	 *
	 */
	public static class ProjectDirectory{
        private final TFile c_dir;

		/**
		 *
		 * @param dir
		 */
		public ProjectDirectory(TFile dir){
            c_dir = dir;
        }

		/**
		 *
		 * @return
		 */
		public TFile getDirectory(){
            return c_dir;
        }
    }
    
}
