package tmcsim.cadsimulator;

import java.io.File;
import java.rmi.RemoteException;
import java.rmi.server.UnicastRemoteObject;
import java.text.DateFormat;
import java.text.SimpleDateFormat;
import java.util.Date;
import java.util.LinkedList;
import java.util.Observer;
import java.util.TreeMap;
import java.util.TreeSet;
import java.util.Vector;
import java.util.logging.Level;
import java.util.logging.Logger;
import javax.swing.table.DefaultTableModel;
import javax.xml.parsers.SAXParserFactory;
import tmcsim.cadmodels.CADRoutedMessage;
import tmcsim.cadmodels.CMSInfo;
import tmcsim.cadmodels.IncidentBoardModel_obj;
import tmcsim.cadmodels.IncidentInquiryModel_obj;
import tmcsim.cadmodels.IncidentInquiryUnitsAssigned;
import tmcsim.cadmodels.IncidentSummaryModel_obj;
import tmcsim.cadsimulator.db.CMSDiversionDB;
import tmcsim.cadsimulator.managers.ATMSManager;
import tmcsim.cadsimulator.managers.IncidentManager;
import tmcsim.cadsimulator.managers.MediaManager;
import tmcsim.cadsimulator.managers.ParamicsSimulationManager;
import tmcsim.cadsimulator.managers.SimulationControlManager;
import tmcsim.cadsimulator.viewer.model.CADSimulatorModel;
import tmcsim.client.cadclientgui.CardfileReader;
import tmcsim.client.cadclientgui.ScriptHandler;
import tmcsim.client.cadclientgui.data.CADData;
import tmcsim.client.cadclientgui.data.CardfileData;
import tmcsim.client.cadclientgui.data.CardfileDataObject;
import tmcsim.client.cadclientgui.data.CardfileList;
import tmcsim.client.cadclientgui.data.ChangeLog;
import tmcsim.client.cadclientgui.data.Incident;
import tmcsim.client.cadclientgui.data.IncidentEvent;
import tmcsim.client.cadclientgui.data.Unit;
import tmcsim.client.cadclientgui.enums.CADDataEnums.CARDFILE;
import tmcsim.client.cadclientgui.enums.CADDataEnums.EditCommand;
import tmcsim.client.cadclientgui.enums.CADDataEnums.INC_ACTIVITIES;
import tmcsim.client.cadclientgui.enums.CADDataEnums.INC_ADD_INFO;
import tmcsim.client.cadclientgui.enums.CADDataEnums.INC_CALLBACK;
import tmcsim.client.cadclientgui.enums.CADDataEnums.INC_CALLER;
import tmcsim.client.cadclientgui.enums.CADDataEnums.INC_EDIT_LOG;
import tmcsim.client.cadclientgui.enums.CADDataEnums.INC_GEN_INFO;
import tmcsim.client.cadclientgui.enums.CADDataEnums.INC_INFO;
import tmcsim.client.cadclientgui.enums.CADDataEnums.INC_LOC;
import tmcsim.client.cadclientgui.enums.CADDataEnums.INC_PROBLEM;
import tmcsim.client.cadclientgui.enums.CADDataEnums.INC_RESP;
import tmcsim.client.cadclientgui.enums.CADDataEnums.INC_TABLE;
import tmcsim.client.cadclientgui.enums.CADDataEnums.INC_TIMES;
import tmcsim.client.cadclientgui.enums.CADDataEnums.INC_VAL;
import tmcsim.client.cadclientgui.enums.CADDataEnums.TABLE;
import tmcsim.client.cadclientgui.enums.CADScriptTags.UNIT_TAGS;
import tmcsim.client.cadclientgui.enums.IncidentEnums;
import tmcsim.client.cadclientgui.enums.UnitStatusEnums;
import tmcsim.common.CADEnums.PARAMICS_STATUS;
import tmcsim.common.CADEnums.SCRIPT_STATUS;
import tmcsim.common.ObserverMessage;
import tmcsim.common.ScriptException;
import tmcsim.common.SimulationException;
import tmcsim.common.XMLIncident;
import tmcsim.interfaces.CADClientInterface;
import tmcsim.interfaces.CoordinatorInterface;
import tmcsim.interfaces.SimulationManagerInterface;

/**
 * Coordinator is used to control and manage interactions between all CAD
 * Simulator Managers. The Coordinator is also registered as an RMI Object to
 * allow remote control and access to simulation data. A
 * SimulationManagerInterface Object is used to provide communication to a
 * remotely connected SimulationManager. Observers may register with the
 * Coordinator to listen for simulation data updates.
 *
 * @see ATMSManager
 * @see IncidentManager
 * @see MediaManager
 * @see ParamicsSimulationManager
 * @see SimulationControlManager
 * @author Matthew Cechini
 * @version
 */
@SuppressWarnings("serial")
public class Coordinator extends UnicastRemoteObject
        implements CoordinatorInterface
{
    /**
     * Error logger.
     */
    private Logger coorLogger = Logger.getLogger("tmcsim.cadsimulator");
    /**
     * List of all Observers that have been registered with the Coordinator. Due
     * to being a remote object, Coordinator cannot extend the Observable class.
     * Therefore, the list is managed manually.
     */
    private Vector<Observer> observerList = null;
    /**
     * Interface object for RMI communication with the Simulation Manager. Only
     * one Simulation Manager may be connected at a time. When there is no
     * connected Manager, this object is set to null.
     */
    private static SimulationManagerInterface managerInt = null;
    private static LinkedList<CADClientInterface> clientList;
    private static CADData cadData;
    private static CardfileData cardfileData;
    private CADSimulatorModel cadModel;

    /**
     * Constructor. Call UnicastRemoteObject constructor and call
     * initializeSimulation.
     *
     * @throws RemoteException
     */
    public Coordinator(CADSimulatorModel model) throws RemoteException
    {
        super();
        cadModel = model;
        clientList = new LinkedList<CADClientInterface>();
        cadData = new CADData();
        cardfileData = new CardfileData();
        try
        {
            CardfileReader cfr = new CardfileReader("scripts/Cardfile.xml", cardfileData);
        } catch (Exception e)
        {
            System.out.println("Could not load cardfile script");
        }

        observerList = new Vector<Observer>();
    }

    /** Dependency Injection for testing */
    void setCadData(CADData theData)
    {
        cadData = theData;
    }
    
    public void registerForCallback(CADClientInterface client) throws RemoteException
    {
        clientList.add(client);
        cadModel.connectClient();
    }

    public void unregisterForCallback(CADClientInterface client) throws RemoteException
    {
        clientList.remove(client);
        cadModel.disconnectClient();
    }

    public void registerForCallback(SimulationManagerInterface simManInt) throws RemoteException
    {
        managerInt = simManInt;
        cadModel.setSimManagerStatus(true);
    }

    public void unregisterForCallback(SimulationManagerInterface simManInt) throws RemoteException
    {
        managerInt = null;
        cadModel.setSimManagerStatus(false);
    }

    public void startSimulation() throws RemoteException, ScriptException
    {

        if (!CADSimulator.theIncidentMgr.areIncidentsLoaded())
        {
            throw new ScriptException(ScriptException.NO_SCRIPT_LOADED);
        }
        else if (CADSimulator.theParamicsSimMgr.isConnected())
        {
            Runnable startRun = new Runnable()
            {
                public void run()
                {
                    try
                    {
                        setScriptStatus(SCRIPT_STATUS.ATMS_SYNCHRONIZATION);

                        /* I have NO idea why this is needed. Why does it get the time from the remote
                         * ATMS server instead of just our system time? Why does it need to sleep?
                         * Is some process happening on the ATMS side that we need to wait for?
                         */
                        long currentATMSTime = CADSimulator.theATMSMgr.getCurrentTime();
                        /* Seems like it waits 0-30 seconds, depending on what the time is on
                         * the ATMS server.  Does something happen every 30 seconds over there?
                         * Was it trying to make the Paramics time the same?
                         */
                        long sleepTime = ((60 * 1000) - (currentATMSTime % (60 * 1000))) % (30 * 1000);

//                        coorLogger.logp(Level.INFO, "Coordinator", "StartSimulation",
//                                "Sleeping for " + sleepTime / 1000 + " seconds.");
                        // not needed   Thread.sleep(sleepTime);

                        //currentATMSTime += sleepTime;
                        //ParamicsCommunicator.getInstance().serverTime.setTimeInMillis(currentATMSTime);
                    } catch (Exception e)
                    {
                        setScriptStatus(SCRIPT_STATUS.SCRIPT_RUNNING);

                        coorLogger.logp(Level.SEVERE, "Coordinator", "StartSimulation:run",
                                "Unable to connect to ATMS server.", e);
                    } finally
                    {
                        CADSimulator.theSimulationCntrlMgr.startSimulation();
                        CADSimulator.theParamicsSimMgr.startSimulation();
                        CADSimulator.theSoundPlayer.setAudioEnabled(true);
                    }
                }
            };

            Thread startThread = new Thread(startRun);
            startThread.start();
        }
        else
        {
            CADSimulator.theSimulationCntrlMgr.startSimulation();
            CADSimulator.theSoundPlayer.setAudioEnabled(true);
        }
    }

    public void pauseSimulation() throws RemoteException
    {
        CADSimulator.theSimulationCntrlMgr.pauseSimulation();
        CADSimulator.theSoundPlayer.setAudioEnabled(false);
    }

    public void resetSimulation() throws RemoteException
    {

        CADSimulator.theIncidentMgr.resetIncidents();
        cadData.resetSimulation();

        CADSimulator.theSoundPlayer.setAudioEnabled(false);
        CADSimulator.theSoundPlayer.deQueueAll();

        cadModel.setTime(0);

        setScriptStatus(SCRIPT_STATUS.SCRIPT_STOPPED_NOT_STARTED);

        CMSDiversionDB.getInstance().resetDiversions();

        CADSimulator.theSimulationCntrlMgr.resetSimulation();
        CADSimulator.theParamicsSimMgr.resetSimulation();

        notifyObservers(new ObserverMessage(ObserverMessage.messageType.RESET_SIMULATION, null));

    }

    public void gotoSimulationTime(final long newSimTime) throws RemoteException
    {

        boolean audioWasEnabled = CADSimulator.theSoundPlayer.getAudioEnabled();

        CADSimulator.theSoundPlayer.setAudioEnabled(false);

        long tempTime = 0;
        while (tempTime < newSimTime)
        {
            tempTime++;

            CADSimulator.theIncidentMgr.tick(tempTime);
        }
        CADSimulator.theSoundPlayer.setAudioEnabled(audioWasEnabled);


        CADSimulator.theSimulationCntrlMgr.gotoSimulationTime(newSimTime);

        Runnable gotoRun = new Runnable()
        {
            public void run()
            {
                cadModel.setTime(newSimTime);

                if (managerInt != null)
                {
                    try
                    {
                        managerInt.tick(newSimTime);
                    } catch (RemoteException re)
                    {
                        //Simulation Manager has disappeared
                        managerInt = null;
                        cadModel.setSimManagerStatus(false);

                        coorLogger.logp(Level.SEVERE, "Coordinator", "gotoSimulationTime:run",
                                "Connection to Simulation Manager has been dropped.", re);
                    }
                }
            }
        };

        Thread gotoThread = new Thread(gotoRun);
        gotoThread.start();

    }

    /**
     * Sets the current script status. A thread is started to notify the
     * CADSimulatorViewer and SimulationManager with the new status.
     */
    public void setScriptStatus(final SCRIPT_STATUS status)
    {

        Runnable updateRun = new Runnable()
        {
            public void run()
            {

                cadModel.setScriptStatus(status);

                if (managerInt != null)
                {
                    try
                    {
                        managerInt.setScriptStatus(status);
                    } catch (RemoteException re)
                    {
                        //Simulation Manager has disappeared
                        managerInt = null;
                        cadModel.setSimManagerStatus(false);

                        coorLogger.logp(Level.SEVERE, "Coordinator", "setScriptStatus:run",
                                "Connection to Simulation Manager has been dropped.", re);
                    }
                }
            }
        };

        Thread updateThread = new Thread(updateRun);
        updateThread.start();
    }

    /**
     * Sets the current paramics status. A thread is started to notify the
     * CADSimulatorViewer and SimulationManager with the new status.
     */
    public void setParamicsStatus(final PARAMICS_STATUS status)
    {

        Runnable updateRun = new Runnable()
        {
            public void run()
            {
                cadModel.setParamicsStatus(status);
                // Is the update for network loaded event?
                // Fixes defect where network ID is never displayed.
                if (status == PARAMICS_STATUS.LOADED)
                {
                    try
                    {
                        // Then we need to tell the model it has a new network ID
                        int currentNetwork = getParamicsNetworkLoaded();
                        cadModel.setParamicsNetworkLoaded("" + currentNetwork);
                    } catch (RemoteException ex)
                    {
                        coorLogger.logp(Level.SEVERE, "Coordinator", "setParamicsStatus:run",
                                "Unable to get current network loaded", ex);
                    }
                }

                if (managerInt != null)
                {
                    try
                    {
                        managerInt.setParamicsStatus(status);
                    } catch (RemoteException re)
                    {
                        //Simulation Manager has disappeared
                        managerInt = null;
                        cadModel.setSimManagerStatus(false);

                        coorLogger.logp(Level.SEVERE, "Coordinator", "setParamicsStatus:run",
                                "Connection to Simulation Manager has been dropped.", re);
                    }
                }
            }
        };

        Thread updateThread = new Thread(updateRun);
        updateThread.start();

    }

    public void connectToParamics() throws RemoteException
    {
        CADSimulator.theParamicsSimMgr.connectToParamics();
    }

    public void disconnectFromParamics() throws RemoteException
    {
        CADSimulator.theParamicsSimMgr.disconnectFromParamics();
    }

    public void loadParamicsNetwork(int networkID) throws RemoteException, SimulationException
    {
        CADSimulator.theParamicsSimMgr.loadParamicsNetwork(networkID);
    }

    public PARAMICS_STATUS getParamicsStatus() throws RemoteException
    {
        return CADSimulator.theParamicsSimMgr.getParamicsStatus();
    }

    public int getParamicsNetworkLoaded() throws RemoteException
    {
        return CADSimulator.theParamicsSimMgr.getParamicsNetworkLoaded();
    }

    public long getCurrentSimulationTime() throws RemoteException
    {
        return CADSimulator.theSimulationCntrlMgr.getCurrentSimTime();
    }

    public void triggerIncident(Integer incidentNumber) throws RemoteException, ScriptException
    {

        if (!CADSimulator.theSimulationCntrlMgr.simulationStarted())
        {
            throw new ScriptException(ScriptException.SIM_NOT_STARTED);
        }
        else if (!CADSimulator.theIncidentMgr.areIncidentsLoaded())
        {
            throw new ScriptException(ScriptException.NO_SCRIPT_LOADED);
        }

        CADSimulator.theIncidentMgr.triggerIncident(incidentNumber,
                CADSimulator.theSimulationCntrlMgr.getCurrentSimTime());
    }

    public void deleteIncident(Integer incidentNumber) throws RemoteException, ScriptException
    {
        CADSimulator.theIncidentMgr.deleteIncident(incidentNumber);

        if (CADSimulator.theIncidentMgr.getIncidentList().size() == 0)
        {
            setScriptStatus(SCRIPT_STATUS.NO_SCRIPT);
        }

        if (managerInt != null)
        {
            try
            {
                managerInt.incidentRemoved(incidentNumber);
            } catch (RemoteException re)
            {
                //Simulation Manager has disappeared
                managerInt = null;
                cadModel.setSimManagerStatus(false);

                coorLogger.logp(Level.SEVERE, "Coordinator", "deleteIncident",
                        "Connection to Simulation Manager has been dropped.", re);
            }
        }
    }

    public void rescheduleIncident(Integer incidentNumber, long newTime)
            throws RemoteException, ScriptException
    {

        if (newTime < CADSimulator.theSimulationCntrlMgr.getCurrentSimTime())
        {
            throw new ScriptException(ScriptException.TIME_PASSED);
        }

        CADSimulator.theIncidentMgr.rescheduleIncident(incidentNumber, newTime);
    }

    public void addIncident(Incident newIncident) throws RemoteException
    {

        CADSimulator.theIncidentMgr.addIncident(newIncident);

        if (managerInt != null)
        {
            try
            {
                managerInt.incidentAdded(newIncident);
            } catch (RemoteException re)
            {
                //Simulation Manager has disappeared
                managerInt = null;
                cadModel.setSimManagerStatus(false);

                coorLogger.logp(Level.SEVERE, "Coordinator", "addIncident",
                        "Connection to Simulation Manager has been dropped.", re);
            }
        }
    }

    public void loadScriptFile(File scriptFile) throws RemoteException, ScriptException
    {


        try
        {
            CADSimulator.theIncidentMgr.clearIncidents();
            cadData.clearData();

            ScriptHandler sh = new ScriptHandler();

            SAXParserFactory.newInstance().newSAXParser().parse(scriptFile, sh);

            cadData.setIncidentsFromXML(sh.getIncidents());
            cadData.setUnitsFromXML(sh.getUnits());
            refreshClients();
            CADSimulator.theIncidentMgr.addIncidents(sh.getIncidents());

            resetSimulation();
        } catch (Exception e)
        {
            e.printStackTrace();
        }

    }

    public Vector<Incident> getIncidentList() throws RemoteException
    {
        return CADSimulator.theIncidentMgr.getIncidentList();
    }

    public TreeMap<Integer, Vector<IncidentEvent>> getTriggeredEvents() throws RemoteException
    {
        return CADSimulator.theIncidentMgr.getTriggeredEvents();
    }

    public SCRIPT_STATUS getScriptStatus() throws RemoteException
    {
        if (CADSimulator.theIncidentMgr.areIncidentsLoaded())
        {
            if (CADSimulator.theSimulationCntrlMgr.simulationStarted())
            {
                return SCRIPT_STATUS.SCRIPT_RUNNING;
            }
            else
            {
                for (Incident inc : CADSimulator.theIncidentMgr.getIncidentList())
                {
                    if (inc.hasOccured() == true)
                    {
                        return SCRIPT_STATUS.SCRIPT_PAUSED_STARTED;
                    }
                }
                return SCRIPT_STATUS.SCRIPT_STOPPED_NOT_STARTED;
            }
        }
        return SCRIPT_STATUS.NO_SCRIPT;
    }

    /**
     * Route a message to a CAD terminal. If the new message is an incident
     * update, the current message text will be the requested incident's log
     * number. Set the message's text to the XML representation of the requested
     * IncidentInquiry object. Notify observers with the new message.
     *
     * @param newMessage Routed message received from CAD Client.
     */
    public void routeMessage(CADRoutedMessage newMessage)
    {

        //if this is an incidentUpdate
        /*
         * TODO  Is this a priority??
         if(newMessage.incidentUpdate) {
         IncidentInquiryModel tempII = new IncidentInquiryModel(
         newMessage.fromPosition,
         CADScreenNum.ONE,
         Integer.parseInt(newMessage.message));

         for(IncidentInquiryModel_obj iimo : getIncidentInquiryModelObjects(
         Integer.parseInt(newMessage.message))) {
         tempII.addModelObject(iimo);
         }

         XMLWriter tempWriter = new XMLWriter();
         tempII.toXML(tempWriter);
         newMessage.message = tempWriter.getString();
         }
         */

        notifyObservers(new ObserverMessage(ObserverMessage.messageType.ROUTED_MESSAGE,
                newMessage));

    }

    public TreeSet<String> getCMSIDs() throws RemoteException
    {
        return new TreeSet<String>(CMSDiversionDB.getInstance().getAllDiversions().keySet());
    }

    public CMSInfo getCMSDiversionInfo(String theCMSID) throws RemoteException
    {
        return CMSDiversionDB.getInstance().getDiversion(theCMSID);
    }

    public void applyDiversions(CMSInfo theDiversion) throws RemoteException
    {
        CMSDiversionDB.getInstance().updateDiversions(theDiversion);
        CADSimulator.theParamicsSimMgr.updateDiversion(theDiversion);
    }

    /**
     * Method updates the simulation with the new Incident information. The
     * parameter IncidentInquiryModel_obj Object is used to create a new
     * IncidentEvent Object which is finalized and sent to the IncidentManager
     * for simulation updating.
     *
     * @param update IncidentInquiryModel_obj containing CAD line update
     * @see IncidentManager
     */
    public void commandLineUpdate(IncidentInquiryModel_obj modelInfo)
    {

        long currentSimTime = CADSimulator.theSimulationCntrlMgr.getCurrentSimTime();

        IncidentEvent triggeredEvent = new IncidentEvent(currentSimTime);
        triggeredEvent.eventInfo = modelInfo;

        triggeredEvent.finalizeEvent(currentSimTime, CADSimulator.getCADTime());

        CADSimulator.theIncidentMgr.updateIncident(modelInfo.getLogNumber(), triggeredEvent);

        updateIncidentInGUI(modelInfo.getLogNumber(), triggeredEvent);

    }

    /**
     * If the Simulation has started, spawn a thread to update the
     * CADSimulatorViewer, SimulationManager, and IncidentManager with the new
     * simulation time. If the current time is a 30 second interval, notify the
     * ParamicsControlManager to send an IncidentUpdate.
     *
     * @see SimulationControlManager
     * @see ParamicsControlManager
     * @see IncidentManager
     */
    public void tick()
    {
        if (CADSimulator.theSimulationCntrlMgr.simulationStarted())
        {

            final long currentSimTime = CADSimulator.theSimulationCntrlMgr.getCurrentSimTime();

            Runnable timeRun = new Runnable()
            {
                public void run()
                {
                    cadModel.setTime(currentSimTime);

                    //send an update every 30 seconds
                    if (currentSimTime % 30 == 0)
                    {
                        CADSimulator.theParamicsSimMgr.sendIncidentUpdate(currentSimTime);
                    }

                    if (managerInt != null)
                    {
                        try
                        {
                            managerInt.tick(currentSimTime);
                        } catch (RemoteException re)
                        {
                            //Simulation Manager has disappeared
                            managerInt = null;
                            cadModel.setSimManagerStatus(false);

                            coorLogger.logp(Level.SEVERE, "Coordinator", "tick:run",
                                    "Connection to Simulation Manager has been dropped.", re);
                        }
                    }

                    CADSimulator.theIncidentMgr.tick(currentSimTime);
                }
            };

            Thread timeThread = new Thread(timeRun);
            timeThread.start();
        }
    }

    /**
     * Method notifies observers with an IncidentSummaryModel_obj to signify
     * that a new Incident has started. Then spawn a thread to notify the
     * SimulationManager with the Incident's log number has started.
     *
     * @param completedEvent Completed IncidentEvent.
     */
    public void incidentStarted(final IncidentEvent completedEvent)
    {
        notifyObservers(new ObserverMessage(ObserverMessage.messageType.INCIDENT_SUMMARY,
                new IncidentSummaryModel_obj(completedEvent.eventInfo.getHeader())));

        incidentStartedInGUI(completedEvent.eventInfo.getLogNumber());

        Runnable startRun = new Runnable()
        {
            public void run()
            {
                if (managerInt != null)
                {
                    try
                    {
                        managerInt.incidentStarted(completedEvent.eventInfo.getLogNumber());
                    } catch (RemoteException re)
                    {
                        //Simulation Manager has disappeared
                        managerInt = null;
                        cadModel.setSimManagerStatus(false);

                        coorLogger.logp(Level.SEVERE, "Coordinator", "updateIncidents",
                                "Connection to Simulation Manager has been dropped.", re);
                    }
                }
            }
        };

        Thread startThread = new Thread(startRun);
        startThread.start();
    }

    /**
     * Method notifies observers with the IncidentEvent Object to signify that a
     * new IncidentEvent has completed. All XMLIncident Objects in the completed
     * IncidentEvent is sent to the ParamicsControlManager for transmission to
     * Paramics. All CCTVInfo Objects are sent to the MediaManager for media
     * control. A thread is then spawned to notify the SimulationManager with
     * the completed IncidentEvent.
     *
     * @param completedEvent Completed IncidentEvent.
     * @see ParamicsControlManager
     * @see MediaManager
     */
    public void incidentUpdated(final IncidentEvent completedEvent)
    {
        notifyObservers(new ObserverMessage(ObserverMessage.messageType.INCIDENT_INQUIRY,
                completedEvent.eventInfo));

        for (XMLIncident xmlInc : completedEvent.XMLIncidents)
        {
            CADSimulator.theParamicsSimMgr.updateIncident(xmlInc);
        }


        /*for(CCTVInfo info : completedEvent.cctvInfos) {
         CADSimulator.theMediaMgr.triggerIncident(info,
         completedEvent.eventInfo.getLogNumber());
         }*/

        Runnable displayRun = new Runnable()
        {
            public void run()
            {
                if (managerInt != null)
                {
                    try
                    {
                        managerInt.eventOccured(
                                completedEvent.eventInfo.getLogNumber(),
                                completedEvent);
                    } catch (RemoteException re)
                    {
                        //Simulation Manager has disappeared
                        managerInt = null;
                        cadModel.setSimManagerStatus(false);

                        coorLogger.logp(Level.SEVERE, "Coordinator", "updateIncidents:run",
                                "Connection to Simulation Manager has been dropped.", re);
                    }
                }
            }
        };

        Thread displayThread = new Thread(displayRun);
        displayThread.start();
    }

    /**
     * @see IncidentManager
     */
    public boolean incidentExists(Integer logNumber)
    {
        return CADSimulator.theIncidentMgr.incidentExists(logNumber);
    }

    /**
     * @see IncidentManager
     */
    public Vector<IncidentBoardModel_obj> getIncidentBoardModelObjects()
    {
        return CADSimulator.theIncidentMgr.getIncidentBoardModelObjects();
    }

    /**
     * @see IncidentManager
     */
    public Vector<IncidentInquiryModel_obj> getIncidentInquiryModelObjects(Integer logNumber)
    {
        return CADSimulator.theIncidentMgr.getIncidentInquiryModelObjects(logNumber);
    }

    /**
     * @see IncidentManager
     */
    public Vector<IncidentSummaryModel_obj> getIncidentSummaryModelObjects()
    {
        return CADSimulator.theIncidentMgr.getIncidentSummaryModelObjects();
    }

    /**
     * Adds an observer to the list of observers.
     *
     * @param o New observer object.
     */
    public void addObserver(Observer o)
    {
        observerList.add(o);
    }

    /**
     * Removes an observer from the list of observers. If the observer is not
     * found, this method returns false, else true is returned for a successful
     * removal.
     *
     * @param o Observer to be removed.
     * @returns True if remove was successful, false if not.
     */
    public boolean removeObserver(Observer o)
    {
        return observerList.remove(o);
    }

    /**
     * Notify all registered observers with the parameter ObserverMessage
     * object.
     *
     * @param newMsg The ObserverMessage to be sent.
     */
    private void notifyObservers(ObserverMessage newMsg)
    {
        for (Observer o : observerList)
        {
            o.update(null, newMsg);
        }
    }

    public void refreshClients() throws RemoteException
    {
        for (int i = 0; i < clientList.size(); i++)
        {
            clientList.get(i).refresh();
        }
    }

    /**
     * Checks the CADData for an existing incident with id
     *
     * @param id the incident id
     * @return true if CADData contains such an incident, otherwise false.
     * @throws RemoteException
     */
    public boolean checkForValidIncidentID(int id) throws RemoteException
    {
        return cadData.checkForValidId(id);
    }

    /**
     * Uses an Incident's masterInc to lookup its ID.
     *
     * @param masterInc the Incident to look up
     * @return the same Incident's ID, -1 if invalid masterInc
     * @throws RemoteException
     */
    public int getIncidentId(String masterInc) throws RemoteException
    {
        return cadData.getIncidentId(masterInc);
    }

    /**
     * Returns a table model out of CADData based on tag.
     *
     * @param tag a CADDataEnums tag
     * @throws RemoteException
     */
    public DefaultTableModel getCadDataTable(TABLE tag) throws RemoteException
    {
        if (tag.equals(TABLE.ASSIGNED_INCIDENTS))
        {
            return cadData.tableForAssignedIncidents();
        }
        else if (tag.equals(TABLE.UNIT_STATUS))
        {
            return cadData.tableForUnitStatus();
        }
        else if (tag.equals(TABLE.PENDING_INCIDENTS))
        {
            return cadData.tableForPendingIncidents();
        }
        else if (tag.equals(TABLE.INCIDENT_EDITOR))
        {
            return cadData.tableForIncidentEditor();
        }
        else
        {
            throw new RemoteException("Wrong Enum sent into Coordinator.getCadDataTable");
        }
    }

    /**
     * Returns the specified incident's table based on the tag.
     *
     * @param tag a CADDataEnums tag
     * @param incidentId the incident's ID to look up
     * @return
     * @throws RemoteException
     */
    public DefaultTableModel getCadDataIncidentTable(INC_TABLE tag, int incidentId) throws RemoteException
    {
        if (tag.equals(INC_TABLE.COMMENTS_NOTES))
        {
            Incident myIncident = cadData.getIncident(incidentId);
            if (myIncident == null) return new DefaultTableModel();
            return myIncident.getCommentsNotesTable();
        }
        return null;
    }

    /**
     * Adds a row of data to a specified incident's table based on the tag.
     *
     * @param tag a CADDataEnums tag
     * @param incidentId the incident's ID to look up
     * @fields the row of fields to add to the specified table
     * @throws RemoteException
     */
    public void addCadDataIncidentTable(INC_TABLE tag, int incidentId, String[] fields) throws RemoteException
    {
        if (tag.equals(INC_TABLE.COMMENTS_NOTES))
        {
            cadData.getIncident(incidentId).addToCommentsNotesTable(fields);
        }
    }

    /**
     * Adds a row to the specified data table based on the incoming fields.
     *
     * @param tag a CADDataEnums tag
     * @param incidentId the incident's ID to look up
     * @throws RemoteException
     */
    public void addCadDataTableRow(TABLE tag, String field1, String field2, String field3, String field4) throws RemoteException
    {
    }

    /**
     * Returns an object out of Incident based on tag.
     *
     * @param tag a CADDataEnums tag
     * @param incidentId the incident's ID to look up
     * @throws RemoteException
     */
    public Object getCadDataIncVal(INC_VAL tag, int incidentId) throws RemoteException
    {
        Incident current = cadData.getIncident(incidentId);
        if (current != null)
        {
            if (tag.equals(INC_VAL.LOG_NUM))
            {
                return current.getLogNum();
            }
            else if (tag.equals(INC_VAL.MASTER_INC))
            {
                return current.getMasterInc();
            }
            else if (tag.equals(INC_VAL.OAU))
            {
                return current.getOau();
            }
            else if (tag.equals(INC_VAL.P))
            {
                return current.getP();
            }
            else if (tag.equals(INC_VAL.DESCRIPTION))
            {
                return current.getDescription();
            }
            else if (tag.equals(INC_VAL.RP))
            {
                return current.getRp();
            }
            else if (tag.equals(INC_VAL.RP_TYPE))
            {
                return current.getRpType();
            }
            else if (tag.equals(INC_VAL.ALI))
            {
                return current.getAli();
            }
            else if (tag.equals(INC_VAL.MEDIA))
            {
                return current.getMedia();
            }
            else
            {
                throw new RemoteException("Wrong Enum sent into Coordinator.getCadDataIncVal");
            }
        }
        else
        {
            return null;
        }
    }

    /**
     * Set incidentId's field based on tag to value.
     *
     * @param tag a CADDataEnums tag
     * @param incidentId the incident's ID to look up
     * @throws RemoteException
     */
    public void setCadDataIncVal(INC_VAL tag, int incidentId, String value) throws RemoteException
    {
        if (tag.equals(INC_VAL.OAU))
        {
            cadData.getIncident(incidentId).setOau(value);
        }
        else if (tag.equals(INC_VAL.P))
        {
            cadData.getIncident(incidentId).setP(value);
        }
        else if (tag.equals(INC_VAL.DESCRIPTION))
        {
            cadData.getIncident(incidentId).setDescription(value);
        }
        else if (tag.equals(INC_VAL.RP))
        {
            cadData.getIncident(incidentId).setRp(value);
        }
        else if (tag.equals(INC_VAL.RP_TYPE))
        {
            cadData.getIncident(incidentId).setRpType(value);
        }
        else if (tag.equals(INC_VAL.ALI))
        {
            cadData.getIncident(incidentId).setAli(value);
        }
        else if (tag.equals(INC_VAL.MEDIA))
        {
            cadData.getIncident(incidentId).setMedia(value);
        }
        else
        {
            throw new RemoteException("Wrong Enum sent into Coordinator.setCadDataIncVal");
        }
    }

    /**
     * Returns a string out of IncidentLocation based on tag.
     *
     * @param tag a CADDataEnums tag
     * @param incidentId the incident's ID to look up
     * @throws RemoteException
     */
    public String getCadDataIncLoc(INC_LOC tag, int incidentId) throws RemoteException
    {
        Incident current = cadData.getIncident(incidentId);
        if (current != null)
        {
            if (tag.equals(INC_LOC.ADDRESS))
            {
                return current.getIncidentLocation().getAddress();
            }
            else if (tag.equals(INC_LOC.LOC))
            {
                return current.getIncidentLocation().getLoc();
            }
            else if (tag.equals(INC_LOC.CITY))
            {
                return current.getIncidentLocation().getCity();
            }
            else if (tag.equals(INC_LOC.COUNTY))
            {
                return current.getIncidentLocation().getCounty();
            }
            else if (tag.equals(INC_LOC.STATE))
            {
                return current.getIncidentLocation().getState();
            }
            else if (tag.equals(INC_LOC.ZIP))
            {
                return current.getIncidentLocation().getZip();
            }
            else if (tag.equals(INC_LOC.BEAT))
            {
                return current.getIncidentLocation().getBeat();
            }
            else if (tag.equals(INC_LOC.AREA))
            {
                return current.getIncidentLocation().getArea();
            }
            else if (tag.equals(INC_LOC.SECTOR))
            {
                return current.getIncidentLocation().getSector();
            }
            else if (tag.equals(INC_LOC.SECTOR_CODE))
            {
                return current.getIncidentLocation().getSectorCode();
            }
            else if (tag.equals(INC_LOC.DIVISION))
            {
                return current.getIncidentLocation().getDivision();
            }
            else if (tag.equals(INC_LOC.APT))
            {
                return current.getIncidentLocation().getApt();
            }
            else if (tag.equals(INC_LOC.BUILDING))
            {
                return current.getIncidentLocation().getBuilding();
            }
            else if (tag.equals(INC_LOC.CROSS_ST))
            {
                return current.getIncidentLocation().getCrossSt();
            }
            else if (tag.equals(INC_LOC.LAW))
            {
                return current.getIncidentLocation().getLaw();
            }
            else if (tag.equals(INC_LOC.FIRE))
            {
                return current.getIncidentLocation().getFire();
            }
            else if (tag.equals(INC_LOC.EMS))
            {
                return current.getIncidentLocation().getEms();
            }
            else
            {
                throw new RemoteException("Wrong Enum sent into Coordinator.getCadDataIncLoc");
            }
        }
        else
        {
            return "";
        }
    }

    /**
     * Set incidentId's field based on tag to value.
     *
     * @param tag a CADDataEnums tag
     * @param incidentId the incident's ID to look up
     * @throws RemoteException
     */
    public void setCadDataIncLoc(INC_LOC tag, int incidentId, String value) throws RemoteException
    {
        Incident current = cadData.getIncident(incidentId);
        if (current != null)
        {
            if (tag.equals(INC_LOC.ADDRESS))
            {
                current.getIncidentLocation().setAddress(value);
            }
            else if (tag.equals(INC_LOC.LOC))
            {
                current.getIncidentLocation().setLoc(value);
            }
            else if (tag.equals(INC_LOC.CITY))
            {
                current.getIncidentLocation().setCity(value);
            }
            else if (tag.equals(INC_LOC.COUNTY))
            {
                current.getIncidentLocation().setCounty(value);
            }
            else if (tag.equals(INC_LOC.STATE))
            {
                current.getIncidentLocation().setState(value);
            }
            else if (tag.equals(INC_LOC.ZIP))
            {
                current.getIncidentLocation().setZip(value);
            }
            else if (tag.equals(INC_LOC.BEAT))
            {
                current.getIncidentLocation().setBeat(value);
            }
            else if (tag.equals(INC_LOC.AREA))
            {
                current.getIncidentLocation().setArea(value);
            }
            else if (tag.equals(INC_LOC.SECTOR))
            {
                current.getIncidentLocation().setSector(value);
            }
            else if (tag.equals(INC_LOC.SECTOR_CODE))
            {
                current.getIncidentLocation().setSectorCode(value);
            }
            else if (tag.equals(INC_LOC.DIVISION))
            {
                current.getIncidentLocation().setDivision(value);
            }
            else if (tag.equals(INC_LOC.APT))
            {
                current.getIncidentLocation().setApt(value);
            }
            else if (tag.equals(INC_LOC.BUILDING))
            {
                current.getIncidentLocation().setBuilding(value);
            }
            else if (tag.equals(INC_LOC.CROSS_ST))
            {
                current.getIncidentLocation().setCrossSt(value);
            }
            else if (tag.equals(INC_LOC.LAW))
            {
                current.getIncidentLocation().setLaw(value);
            }
            else if (tag.equals(INC_LOC.FIRE))
            {
                current.getIncidentLocation().setFire(value);
            }
            else if (tag.equals(INC_LOC.EMS))
            {
                current.getIncidentLocation().setEms(value);
            }
            else
            {
                throw new RemoteException("Wrong Enum sent into Coordinator.setCadDataIncLoc");
            }
        }
        else
        {
            return;
        }
    }

    /**
     * Returns a string out of IncidentCaller based on tag.
     *
     * @param tag a CADDataEnums tag
     * @param incidentId the incident's ID to look up
     * @throws RemoteException
     */
    public String getCadDataIncCaller(INC_CALLER tag, int incidentId) throws RemoteException
    {
        if (tag.equals(INC_CALLER.TYPE))
        {
            return cadData.getIncident(incidentId).getIncidentCaller().getCallerType();
        }
        else if (tag.equals(INC_CALLER.NAME))
        {
            return cadData.getIncident(incidentId).getIncidentCaller().getCallerName();
        }
        else if (tag.equals(INC_CALLER.PHONE))
        {
            return cadData.getIncident(incidentId).getIncidentCaller().getPhone();
        }
        else if (tag.equals(INC_CALLER.EXT))
        {
            return cadData.getIncident(incidentId).getIncidentCaller().getExt();
        }
        else
        {
            throw new RemoteException("Wrong Enum sent into Coordinator.getCadDataIncCaller");
        }
    }

    /**
     * Set incidentId's field based on tag to value.
     *
     * @param tag a CADDataEnums tag
     * @param incidentId the incident's ID to look up
     * @throws RemoteException
     */
    public void setCadDataIncCaller(INC_CALLER tag, int incidentId, String value) throws RemoteException
    {
        if (tag.equals(INC_CALLER.TYPE))
        {
            cadData.getIncident(incidentId).getIncidentCaller().setCallerType(value);
        }
        else if (tag.equals(INC_CALLER.NAME))
        {
            cadData.getIncident(incidentId).getIncidentCaller().setCallerName(value);
        }
        else if (tag.equals(INC_CALLER.PHONE))
        {
            cadData.getIncident(incidentId).getIncidentCaller().setPhone(value);
        }
        else if (tag.equals(INC_CALLER.EXT))
        {
            cadData.getIncident(incidentId).getIncidentCaller().setExt(value);
        }
        else
        {
            throw new RemoteException("Wrong Enum sent into Coordinator.setCadDataIncCaller");
        }
    }

    /**
     * Returns a string out of IncidentProblem based on tag.
     *
     * @param tag a CADDataEnums tag
     * @param incidentId the incident's ID to look up
     * @throws RemoteException
     */
    public String getCadDataIncProblem(INC_PROBLEM tag, int incidentId) throws RemoteException
    {
        if (tag.equals(INC_PROBLEM.PROBLEM))
        {
            return cadData.getIncident(incidentId).getProblem().getProblem();
        }
        else if (tag.equals(INC_PROBLEM.CODE))
        {
            return cadData.getIncident(incidentId).getProblem().getProblemCode();
        }
        else if (tag.equals(INC_PROBLEM.PRIORITY))
        {
            return cadData.getIncident(incidentId).getProblem().getPriority();
        }
        else
        {
            throw new RemoteException("Wrong Enum sent into Coordinator.getCadDataIncProblem");
        }
    }

    /**
     * Set incidentId's field based on tag to value.
     *
     * @param tag a CADDataEnums tag
     * @param incidentId the incident's ID to look up
     * @throws RemoteException
     */
    public void setCadDataIncProblem(INC_PROBLEM tag, int incidentId, String value) throws RemoteException
    {
        if (tag.equals(INC_PROBLEM.PROBLEM))
        {
            cadData.getIncident(incidentId).getProblem().setProblem(value);
        }
        else if (tag.equals(INC_PROBLEM.CODE))
        {
            cadData.getIncident(incidentId).getProblem().setProblemCode(value);
        }
        else if (tag.equals(INC_PROBLEM.PRIORITY))
        {
            cadData.getIncident(incidentId).getProblem().setPriority(value);
        }
        else
        {
            throw new RemoteException("Wrong Enum sent into Coordinator.setCadDataIncProblem");
        }
    }

    /**
     * Returns a string out of IncidentGeneralInfo based on tag.
     *
     * @param tag a CADDataEnums tag
     * @param incidentId the incident's ID to look up
     * @throws RemoteException
     */
    public String getCadDataIncGenInfo(INC_GEN_INFO tag, int incidentId) throws RemoteException
    {
        if (tag.equals(INC_GEN_INFO.JURISDICTION))
        {
            return cadData.getIncident(incidentId).getGenInfo().getJurisdiction();
        }
        else if (tag.equals(INC_GEN_INFO.ALARM))
        {
            return cadData.getIncident(incidentId).getGenInfo().getAlarm();
        }
        else if (tag.equals(INC_GEN_INFO.AGY))
        {
            return cadData.getIncident(incidentId).getGenInfo().getAgy();
        }
        else
        {
            throw new RemoteException("Wrong Enum sent into Coordinator.getCadDataIncGenInfo");
        }
    }

    /**
     * Set incidentId's field based on tag to value.
     *
     * @param tag a CADDataEnums tag
     * @param incidentId the incident's ID to look up
     * @throws RemoteException
     */
    public void setCadDataIncGenInfo(INC_GEN_INFO tag, int incidentId, String value) throws RemoteException
    {
        if (tag.equals(INC_GEN_INFO.JURISDICTION))
        {
            cadData.getIncident(incidentId).getGenInfo().setJurisdiction(value);
        }
        else if (tag.equals(INC_GEN_INFO.ALARM))
        {
            cadData.getIncident(incidentId).getGenInfo().setAlarm(value);
        }
        else if (tag.equals(INC_GEN_INFO.AGY))
        {
            cadData.getIncident(incidentId).getGenInfo().setAgy(value);
        }
        else
        {
            throw new RemoteException("Wrong Enum sent into Coordinator.setCadDataIncGenInfo");
        }
    }

    /**
     * Returns a string out of IncidentResponse based on tag.
     *
     * @param tag a CADDataEnums tag
     * @param incidentId the incident's ID to look up
     * @throws RemoteException
     */
    public String getCadDataIncResp(INC_RESP tag, int incidentId) throws RemoteException
    {
        if (tag.equals(INC_RESP.PLAN))
        {
            return cadData.getIncident(incidentId).getResponse().getPlan();
        }
        else if (tag.equals(INC_RESP.AREA))
        {
            return cadData.getIncident(incidentId).getResponse().getArea();
        }
        else
        {
            throw new RemoteException("Wrong Enum sent into Coordinator.getCadDataIncResp");
        }
    }

    /**
     * Set incidentId's field based on tag to value.
     *
     * @param tag a CADDataEnums tag
     * @param incidentId the incident's ID to look up
     * @throws RemoteException
     */
    public void setCadDataIncResp(INC_RESP tag, int incidentId, String value) throws RemoteException
    {
        if (tag.equals(INC_RESP.PLAN))
        {
            cadData.getIncident(incidentId).getResponse().setPlan(value);
        }
        else if (tag.equals(INC_RESP.AREA))
        {
            cadData.getIncident(incidentId).getResponse().setArea(value);
        }
        else
        {
            throw new RemoteException("Wrong Enum sent into Coordinator.setCadDataIncResp");
        }
    }

    /**
     * Returns a string out of IncidentAdditionalInfo based on tag.
     *
     * @param tag a CADDataEnums tag
     * @param incidentId the incident's ID to look up
     * @throws RemoteException
     */
    public String getCadDataIncAddInfo(INC_ADD_INFO tag, int incidentId) throws RemoteException
    {
        if (tag.equals(INC_ADD_INFO.TYPE))
        {
            return cadData.getIncident(incidentId).getAdditionalInfo().getType();
        }
        else if (tag.equals(INC_ADD_INFO.TYPE_CODE))
        {
            return cadData.getIncident(incidentId).getAdditionalInfo().getTypeCode();
        }
        else if (tag.equals(INC_ADD_INFO.MACHINE))
        {
            return cadData.getIncident(incidentId).getAdditionalInfo().getMachine();
        }
        else if (tag.equals(INC_ADD_INFO.CALL_STATUS))
        {
            return cadData.getIncident(incidentId).getAdditionalInfo().getCallStatus();
        }
        else if (tag.equals(INC_ADD_INFO.CALL_TAKER_EXT))
        {
            return cadData.getIncident(incidentId).getAdditionalInfo().getCallTakerExt();
        }
        else if (tag.equals(INC_ADD_INFO.ALARM_LEVEL))
        {
            return cadData.getIncident(incidentId).getAdditionalInfo().getAlarmLevel();
        }
        else if (tag.equals(INC_ADD_INFO.ROTATION_PROVIDER_AREA))
        {
            return cadData.getIncident(incidentId).getAdditionalInfo().getRotationProviderArea();
        }
        else if (tag.equals(INC_ADD_INFO.COMMENT))
        {
            return cadData.getIncident(incidentId).getAdditionalInfo().getComment();
        }
        else
        {
            throw new RemoteException("Wrong Enum sent into Coordinator.getCadDataIncAddInfo");
        }
    }

    /**
     * Set incidentId's field based on tag to value.
     *
     * @param tag a CADDataEnums tag
     * @param incidentId the incident's ID to look up
     * @throws RemoteException
     */
    public void setCadDataIncAddInfo(INC_ADD_INFO tag, int incidentId, String value) throws RemoteException
    {
        if (tag.equals(INC_ADD_INFO.TYPE))
        {
            cadData.getIncident(incidentId).getAdditionalInfo().setType(value);
        }
        else if (tag.equals(INC_ADD_INFO.TYPE_CODE))
        {
            cadData.getIncident(incidentId).getAdditionalInfo().setTypeCode(value);
        }
        else if (tag.equals(INC_ADD_INFO.MACHINE))
        {
            cadData.getIncident(incidentId).getAdditionalInfo().setMachine(value);
        }
        else if (tag.equals(INC_ADD_INFO.CALL_STATUS))
        {
            cadData.getIncident(incidentId).getAdditionalInfo().setCallStatus(value);
        }
        else if (tag.equals(INC_ADD_INFO.CALL_TAKER_EXT))
        {
            cadData.getIncident(incidentId).getAdditionalInfo().setCallTakerExt(value);
        }
        else if (tag.equals(INC_ADD_INFO.ALARM_LEVEL))
        {
            cadData.getIncident(incidentId).getAdditionalInfo().setAlarmLevel(value);
        }
        else if (tag.equals(INC_ADD_INFO.ROTATION_PROVIDER_AREA))
        {
            cadData.getIncident(incidentId).getAdditionalInfo().setRotationProviderArea(value);
        }
        else if (tag.equals(INC_ADD_INFO.COMMENT))
        {
            cadData.getIncident(incidentId).getAdditionalInfo().setComment(value);
        }
        else
        {
            throw new RemoteException("Wrong Enum sent into Coordinator.setCadDataIncAddInfo");
        }
    }

    /**
     * Returns a string out of IncidentActivities based on tag.
     *
     * @param tag a CADDataEnums tag
     * @param incidentId the incident's ID to look up
     * @throws RemoteException
     */
    public String getCadDataIncActivities(INC_ACTIVITIES tag, int incidentId) throws RemoteException
    {
        if (tag.equals(INC_ACTIVITIES.VEHICLE))
        {
            return cadData.getIncident(incidentId).getActivities().getVehicle();
        }
        else if (tag.equals(INC_ACTIVITIES.ACTIVITY))
        {
            return cadData.getIncident(incidentId).getActivities().getActivity();
        }
        else if (tag.equals(INC_ACTIVITIES.LOCATION))
        {
            return cadData.getIncident(incidentId).getActivities().getLocation();
        }
        else if (tag.equals(INC_ACTIVITIES.COMMENT))
        {
            return cadData.getIncident(incidentId).getActivities().getComment();
        }
        else if (tag.equals(INC_ACTIVITIES.DISP))
        {
            return cadData.getIncident(incidentId).getActivities().getDisp();
        }
        else
        {
            throw new RemoteException("Wrong Enum sent into Coordinator.getCadDataIncActivities");
        }
    }

    /**
     * Set incidentId's field based on tag to value.
     *
     * @param tag a CADDataEnums tag
     * @param incidentId the incident's ID to look up
     * @throws RemoteException
     */
    public void setCadDataIncActivities(INC_ACTIVITIES tag, int incidentId, String value) throws RemoteException
    {
        if (tag.equals(INC_ACTIVITIES.VEHICLE))
        {
            cadData.getIncident(incidentId).getActivities().setVehicle(value);
        }
        else if (tag.equals(INC_ACTIVITIES.ACTIVITY))
        {
            cadData.getIncident(incidentId).getActivities().setActivity(value);
        }
        else if (tag.equals(INC_ACTIVITIES.LOCATION))
        {
            cadData.getIncident(incidentId).getActivities().setLocation(value);
        }
        else if (tag.equals(INC_ACTIVITIES.COMMENT))
        {
            cadData.getIncident(incidentId).getActivities().setComment(value);
        }
        else if (tag.equals(INC_ACTIVITIES.DISP))
        {
            cadData.getIncident(incidentId).getActivities().setDisp(value);
        }
        else
        {
            throw new RemoteException("Wrong Enum sent into Coordinator.setCadDataIncActivities");
        }
    }

    /**
     * Returns a string out of IncidentCallback based on tag.
     *
     * @param tag a CADDataEnums tag
     * @param incidentId the incident's ID to look up
     * @throws RemoteException
     */
    public String getCadDataIncCallBack(INC_CALLBACK tag, int incidentId) throws RemoteException
    {
        if (tag.equals(INC_CALLBACK.INITIAL))
        {
            return cadData.getIncident(incidentId).getCallBacks().getInitial();
        }
        else if (tag.equals(INC_CALLBACK.COMMENT))
        {
            return cadData.getIncident(incidentId).getCallBacks().getComment();
        }
        else
        {
            throw new RemoteException("Wrong Enum sent into Coordinator.getCadDataIncCallBack");
        }
    }

    /**
     * Returns a string out of IncidentEditLog based on tag.
     *
     * @param tag a CADDataEnums tag
     * @param incidentId the incident's ID to look up
     * @throws RemoteException
     */
    public String getCadDataIncEditLog(INC_EDIT_LOG tag, int incidentId) throws RemoteException
    {
        if (tag.equals(INC_EDIT_LOG.EDIT))
        {
            return cadData.getIncident(incidentId).getEditLog().getEdit();
        }
        else if (tag.equals(INC_EDIT_LOG.REASON))
        {
            return cadData.getIncident(incidentId).getEditLog().getReason();
        }
        else if (tag.equals(INC_EDIT_LOG.CHANGE_BY))
        {
            return cadData.getIncident(incidentId).getEditLog().getChangeBy();
        }
        else if (tag.equals(INC_EDIT_LOG.TERMINAL))
        {
            return cadData.getIncident(incidentId).getEditLog().getTerminal();
        }
        else
        {
            throw new RemoteException("Wrong Enum sent into Coordinator.getCadDataIncEditLog");
        }
    }

    /**
     * Returns a string out of IncidentInfo based on tag.
     *
     * @param tag a CADDataEnums tag
     * @param incidentId the incident's ID to look up
     * @throws RemoteException
     */
    public String getCadDataIncInfo(INC_INFO tag, int incidentId) throws RemoteException
    {
        if (tag.equals(INC_INFO.CALL_INITIATED))
        {
            return cadData.getIncident(incidentId).getInfo().getCallInit();
        }
        else if (tag.equals(INC_INFO.CALL_TAKEN))
        {
            return cadData.getIncident(incidentId).getInfo().getCallTaken();
        }
        else if (tag.equals(INC_INFO.TIME_IN_Q))
        {
            return cadData.getIncident(incidentId).getInfo().getTimeInQ();
        }
        else if (tag.equals(INC_INFO.LAST_UPDATED))
        {
            return cadData.getIncident(incidentId).getInfo().getLastUpdated();
        }
        else
        {
            throw new RemoteException("Wrong Enum sent into Coordinator.getCadDataIncInfo");
        }
    }

    /**
     * Returns a string out of IncidentTimes based on tag.
     *
     * @param tag a CADDataEnums tag
     * @param incidentId the incident's ID to look up
     * @throws RemoteException
     */
    public String getCadDataIncTimes(INC_TIMES tag, int incidentId) throws RemoteException
    {
        // TODO Auto-generated method stub
        return null;
    }

    /**
     * Returns a CardfileList matching the tag.
     */
    public CardfileList getCardfileList(CARDFILE tag) throws RemoteException
    {
        if (tag.equals(CARDFILE.COASTAL_DIVISION_UNITS))
        {
            return cardfileData.getCoastalDivisionUnitList();
        }
        else if (tag.equals(CARDFILE.POLICE_SHERIFF_CORONER))
        {
            return cardfileData.getPoliceSheriffCoronerList();
        }
        else if (tag.equals(CARDFILE.COURTS))
        {
            return cardfileData.getCourtsList();
        }
        else if (tag.equals(CARDFILE.PUBLIC_TRANSPORTATION))
        {
            return cardfileData.getPublicTransportationList();
        }
        else if (tag.equals(CARDFILE.GG_OTHER))
        {
            return cardfileData.getGgOtherList();
        }
        else if (tag.equals(CARDFILE.MY_MISC))
        {
            return cardfileData.getMyMiscList();
        }
        else if (tag.equals(CARDFILE.SL_MISC))
        {
            return cardfileData.getSlMiscList();
        }
        else if (tag.equals(CARDFILE.VT_MISC))
        {
            return cardfileData.getVlMiscList();
        }
        else if (tag.equals(CARDFILE.CHP_OFFICES))
        {
            return cardfileData.getChpOfficesList();
        }
        else if (tag.equals(CARDFILE.STATE_AGENCIES_FACILITIES))
        {
            return cardfileData.getStateAgenciesFacilitiesList();
        }
        else if (tag.equals(CARDFILE.GOVERNMENT_OFFICIALS))
        {
            return cardfileData.getGovernmentOfficialsList();
        }
        else if (tag.equals(CARDFILE.FEDERAL_AGENCIES))
        {
            return cardfileData.getFederalAgenciesList();
        }
        else if (tag.equals(CARDFILE.RANCHES_LIVESTOCK))
        {
            return cardfileData.getRanchesLivestockList();
        }
        else if (tag.equals(CARDFILE.FIRE_EMS))
        {
            return cardfileData.getFireEmsList();
        }
        else if (tag.equals(CARDFILE.JAILS))
        {
            return cardfileData.getJailsList();
        }
        else if (tag.equals(CARDFILE.HOSPITALS_MED_CENTERS))
        {
            return cardfileData.getHospitalsMedCentersList();
        }
        else if (tag.equals(CARDFILE.TOW_COMPANIES))
        {
            return cardfileData.getTowCompaniesList();
        }
        else if (tag.equals(CARDFILE.CALTRANS))
        {
            return cardfileData.getCalTransList();
        }
        else if (tag.equals(CARDFILE.COUNTY_ROADS))
        {
            return cardfileData.getCountyRoadsList();
        }
        else if (tag.equals(CARDFILE.UTILITIES))
        {
            return cardfileData.getUtilitiesList();
        }
        else if (tag.equals(CARDFILE.ANIMAL_CONTROL))
        {
            return cardfileData.getAnimalControlList();
        }
        else if (tag.equals(CARDFILE.AIRPORTS))
        {
            return cardfileData.getAirportsList();
        }
        else if (tag.equals(CARDFILE.CREDIT_CARDS))
        {
            return cardfileData.getCreditCardsList();
        }
        else if (tag.equals(CARDFILE.GG_CRISIS_SHELTERS))
        {
            return cardfileData.getGgCrisisSheltersList();
        }
        else if (tag.equals(CARDFILE.RANGES))
        {
            return cardfileData.getRangesList();
        }
        else if (tag.equals(CARDFILE.HOTLINES))
        {
            return cardfileData.getHotlinesList();
        }
        else if (tag.equals(CARDFILE.HWY_PATROLS_OOS))
        {
            return cardfileData.getHwyPatrolsOosList();
        }
        else if (tag.equals(CARDFILE.PARKS_RECREATION))
        {
            return cardfileData.getParksRecreationList();
        }
        else if (tag.equals(CARDFILE.SHELTERS))
        {
            return cardfileData.getSheltersList();
        }
        else if (tag.equals(CARDFILE.SL_COUNTY_SERVICES))
        {
            return cardfileData.getSlCountyServicesList();
        }
        else if (tag.equals(CARDFILE.SL_RESOURCES))
        {
            return cardfileData.getSlResourcesList();
        }
        else if (tag.equals(CARDFILE.TRUCK_TIRE_REPAIR))
        {
            return cardfileData.getTruckTireRepairList();
        }
        else if (tag.equals(CARDFILE.MCC_EMPLOYEES))
        {
            return cardfileData.getMccEmployeesList();
        }
        else if (tag.equals(CARDFILE.GATE_ACCESS_CODES))
        {
            return cardfileData.getGateAccessCodesList();
        }
        else if (tag.equals(CARDFILE.VT_CALL_SIGNS))
        {
            return cardfileData.getVtCallSignsList();
        }
        else if (tag.equals(CARDFILE.SLCC_EMPLOYEES))
        {
            return cardfileData.getSlccEmployeesList();
        }
        else
        {
            throw new RemoteException("Wrong Enum sent into Coordinator.getCardfileList");
        }
    }

    /**
     * Receives the fields of the ChangeLog in Cardfile.java and uses those
     * fields to make changes to its own copy of the Cardfiledata.
     */
    public void editCardfile(ChangeLog log) throws RemoteException
    {

        CardfileList selectedList;

        if (log.listTitle.equals(CARDFILE.COASTAL_DIVISION_UNITS.tag))
        {
            selectedList = cardfileData.getCoastalDivisionUnitList();
        }
        else if (log.listTitle.equals(CARDFILE.POLICE_SHERIFF_CORONER.tag))
        {
            selectedList = cardfileData.getPoliceSheriffCoronerList();
        }
        else if (log.listTitle.equals(CARDFILE.COURTS.tag))
        {
            selectedList = cardfileData.getCourtsList();
        }
        else if (log.listTitle.equals(CARDFILE.PUBLIC_TRANSPORTATION.tag))
        {
            selectedList = cardfileData.getPublicTransportationList();
        }
        else if (log.listTitle.equals(CARDFILE.GG_OTHER.tag))
        {
            selectedList = cardfileData.getGgOtherList();
        }
        else if (log.listTitle.equals(CARDFILE.MY_MISC.tag))
        {
            selectedList = cardfileData.getMyMiscList();
        }
        else if (log.listTitle.equals(CARDFILE.SL_MISC.tag))
        {
            selectedList = cardfileData.getSlMiscList();
        }
        else if (log.listTitle.equals(CARDFILE.VT_MISC.tag))
        {
            selectedList = cardfileData.getVlMiscList();
        }
        else if (log.listTitle.equals(CARDFILE.CHP_OFFICES.tag))
        {
            selectedList = cardfileData.getChpOfficesList();
        }
        else if (log.listTitle.equals(CARDFILE.STATE_AGENCIES_FACILITIES.tag))
        {
            selectedList = cardfileData.getStateAgenciesFacilitiesList();
        }
        else if (log.listTitle.equals(CARDFILE.GOVERNMENT_OFFICIALS.tag))
        {
            selectedList = cardfileData.getGovernmentOfficialsList();
        }
        else if (log.listTitle.equals(CARDFILE.FEDERAL_AGENCIES.tag))
        {
            selectedList = cardfileData.getFederalAgenciesList();
        }
        else if (log.listTitle.equals(CARDFILE.RANCHES_LIVESTOCK.tag))
        {
            selectedList = cardfileData.getRanchesLivestockList();
        }
        else if (log.listTitle.equals(CARDFILE.FIRE_EMS.tag))
        {
            selectedList = cardfileData.getFireEmsList();
        }
        else if (log.listTitle.equals(CARDFILE.JAILS.tag))
        {
            selectedList = cardfileData.getJailsList();
        }
        else if (log.listTitle.equals(CARDFILE.HOSPITALS_MED_CENTERS.tag))
        {
            selectedList = cardfileData.getHospitalsMedCentersList();
        }
        else if (log.listTitle.equals(CARDFILE.TOW_COMPANIES.tag))
        {
            selectedList = cardfileData.getTowCompaniesList();
        }
        else if (log.listTitle.equals(CARDFILE.CALTRANS.tag))
        {
            selectedList = cardfileData.getCalTransList();
        }
        else if (log.listTitle.equals(CARDFILE.COUNTY_ROADS.tag))
        {
            selectedList = cardfileData.getCountyRoadsList();
        }
        else if (log.listTitle.equals(CARDFILE.UTILITIES.tag))
        {
            selectedList = cardfileData.getUtilitiesList();
        }
        else if (log.listTitle.equals(CARDFILE.ANIMAL_CONTROL.tag))
        {
            selectedList = cardfileData.getAnimalControlList();
        }
        else if (log.listTitle.equals(CARDFILE.AIRPORTS.tag))
        {
            selectedList = cardfileData.getAirportsList();
        }
        else if (log.listTitle.equals(CARDFILE.CREDIT_CARDS.tag))
        {
            selectedList = cardfileData.getCreditCardsList();
        }
        else if (log.listTitle.equals(CARDFILE.GG_CRISIS_SHELTERS.tag))
        {
            selectedList = cardfileData.getGgCrisisSheltersList();
        }
        else if (log.listTitle.equals(CARDFILE.RANGES.tag))
        {
            selectedList = cardfileData.getRangesList();
        }
        else if (log.listTitle.equals(CARDFILE.HOTLINES.tag))
        {
            selectedList = cardfileData.getHotlinesList();
        }
        else if (log.listTitle.equals(CARDFILE.HWY_PATROLS_OOS.tag))
        {
            selectedList = cardfileData.getHwyPatrolsOosList();
        }
        else if (log.listTitle.equals(CARDFILE.PARKS_RECREATION.tag))
        {
            selectedList = cardfileData.getParksRecreationList();
        }
        else if (log.listTitle.equals(CARDFILE.SHELTERS.tag))
        {
            selectedList = cardfileData.getSheltersList();
        }
        else if (log.listTitle.equals(CARDFILE.SL_COUNTY_SERVICES.tag))
        {
            selectedList = cardfileData.getSlCountyServicesList();
        }
        else if (log.listTitle.equals(CARDFILE.SL_RESOURCES.tag))
        {
            selectedList = cardfileData.getSlResourcesList();
        }
        else if (log.listTitle.equals(CARDFILE.TRUCK_TIRE_REPAIR.tag))
        {
            selectedList = cardfileData.getTruckTireRepairList();
        }
        else if (log.listTitle.equals(CARDFILE.MCC_EMPLOYEES.tag))
        {
            selectedList = cardfileData.getMccEmployeesList();
        }
        else if (log.listTitle.equals(CARDFILE.GATE_ACCESS_CODES.tag))
        {
            selectedList = cardfileData.getGateAccessCodesList();
        }
        else if (log.listTitle.equals(CARDFILE.VT_CALL_SIGNS.tag))
        {
            selectedList = cardfileData.getVtCallSignsList();
        }
        else if (log.listTitle.equals(CARDFILE.SLCC_EMPLOYEES.tag))
        {
            selectedList = cardfileData.getSlccEmployeesList();
        }
        else
        {
            throw new RemoteException("Wrong Enum sent into Coordinator.editCardfileDataObject");
        }

        CardfileDataObject cfdo = cardfileData.getCardfileDataObject(selectedList, log.id);
        if (cfdo != null && log.command.equals(EditCommand.NAME))
        {
            cfdo.setName(log.newValue);
            selectedList.resort(cardfileData.getCardfileDataIndex(selectedList, log.id));
        }
        else if (cfdo != null && log.command.equals(EditCommand.ADDRESS))
        {
            cfdo.setAddress(log.newValue);
        }
        else if (cfdo != null && log.command.equals(EditCommand.CITY))
        {
            cfdo.setCity(log.newValue);
        }
        else if (cfdo != null && log.command.equals(EditCommand.STATE))
        {
            cfdo.setState(log.newValue);
        }
        else if (cfdo != null && log.command.equals(EditCommand.ZIP))
        {
            cfdo.setZip(log.newValue);
        }
        else if (cfdo != null && log.command.equals(EditCommand.PHONE1))
        {
            cfdo.setPhone1(log.newValue);
        }
        else if (cfdo != null && log.command.equals(EditCommand.PHONE2))
        {
            cfdo.setPhone2(log.newValue);
        }
        else if (cfdo != null && log.command.equals(EditCommand.FAX))
        {
            cfdo.setFax(log.newValue);
        }
        else if (log.command.equals(EditCommand.OBJECT_DELETE))
        {
            selectedList.removeDataObject(cardfileData.getCardfileDataIndex(selectedList, log.id));
        }
        else if (log.command.equals(EditCommand.OBJECT_ADD))
        {
            selectedList.addDataObject(log.newCardfileObject);
        }
        else if (log.command.equals(EditCommand.TABLE_ADD))
        {
            if (cfdo != null)
            {
                cfdo.addComment(log.tableFields);
            }
        }
        else if (log.command.equals(EditCommand.TABLE_DELETE))
        {
            if (cfdo != null)
            {
                cfdo.removeComment(log.timeStamp);
            }
        }
        else
        {
        }


    }

    /**
     * Obtain a new unique ID for a cardfileDataObject.
     */
    public int obtainNewUniqueId() throws RemoteException
    {
        return cardfileData.obtainNewUniqueId();
    }

    /**
     * Returns a value from Unit based on tag.
     *
     * @param unitNum the unitNum to look up
     * @throws RemoteException
     */
    public UnitStatusEnums getCadDataUnitStatus(String unitNum) throws RemoteException
    {
        // Validate input parameter
        if (unitNum.equals(""))
        {
            coorLogger.logp(Level.INFO, "Coordinator", "getCadDataUnitStatus",
                        "Unitnum parameter is blank.", "Error");
            return UnitStatusEnums.NotAssignable;
        }
        else
        {
            Unit desiredUnit = cadData.getUnit(unitNum);
            // If it exists
            if (desiredUnit != null)
            {
                // Fetch and return its status (an enum)
                return desiredUnit.getUnitStatus();
            }
            else
            {
                return UnitStatusEnums.NotAssignable;
            }
        }
    }

    /**
     * Returns a string field from Unit based on tag.
     *
     * @param tag a CADScriptTags tag
     * @param unitNum the unitNum to look up
     * @return a string value
     * @throws RemoteException
     */
    public String getCadDataUnitValue(String unitNum, UNIT_TAGS tag) throws RemoteException
    {
        // Fetch unit, given it's string representation
        Unit desiredUnit = cadData.getUnit(unitNum);
        // If it exists
        if (desiredUnit != null)
        {
            if (tag.equals(UNIT_TAGS.MASTER_INC_NUM))
            {
                return desiredUnit.getMasterInc();
            }
            else if (tag.equals(UNIT_TAGS.STATUS))
            {
                return desiredUnit.getStatus();
            }
            else if (tag.equals(UNIT_TAGS.OOS))
            {
                return desiredUnit.getOos();
            }
            else if (tag.equals(UNIT_TAGS.TYPE))
            {
                return desiredUnit.getType();
            }
            else if (tag.equals(UNIT_TAGS.CURR_LOC))
            {
                return desiredUnit.getCurrentLocation();
            }
            else if (tag.equals(UNIT_TAGS.DESTINATION))
            {
                return desiredUnit.getDestination();
            }
            else if (tag.equals(UNIT_TAGS.MISC_INFO))
            {
                return desiredUnit.getMisc();
            }
            else if (tag.equals(UNIT_TAGS.STACK))
            {
                return desiredUnit.getStack();
            }
            else if (tag.equals(UNIT_TAGS.AREA))
            {
                return desiredUnit.getArea();
            }
            else if (tag.equals(UNIT_TAGS.OFFICER))
            {
                return desiredUnit.getOfficer();
            }
            else if (tag.equals(UNIT_TAGS.BADGE_NUM))
            {
                return desiredUnit.getBadge();
            }
            else if (tag.equals(UNIT_TAGS.TIMER))
            {
                return desiredUnit.getTimerInString();
            }
            else if (tag.equals(UNIT_TAGS.OFFICE))
            {
                return desiredUnit.getOffice();
            }
            else if (tag.equals(UNIT_TAGS.P))
            {
                return desiredUnit.getP();
            }
            else if (tag.equals(UNIT_TAGS.AGY))
            {
                return desiredUnit.getAgy();
            }
            else if (tag.equals(UNIT_TAGS.ALIAS))
            {
                return desiredUnit.getAlias();
            }
            else
            {
                throw new RemoteException("Wrong Enum sent into Coordinator.getCadDataUnitValue");
            }
        }
        else
        {
            coorLogger.logp(Level.INFO, "Coordinator", "getCadDataUnitValue",
                    "Desired unit not found: " + unitNum
                    + ". Proceeding with empty string value.", "Error");
            return "";
        }
    }

    /**
     * Sets a field from Unit based on tag.
     *
     * @param tag a CADScriptTags tag
     * @param unitNum the unitNum to look up
     * @param value the new value to be set
     * @throws RemoteException
     */
    public void setCadDataUnitValue(String unitNum, UNIT_TAGS tag, Object value) throws RemoteException
    {
        if (tag.equals(UNIT_TAGS.MASTER_INC_NUM))
        {
            cadData.getUnit(unitNum).setMasterInc((String) value);
        }
        else if (tag.equals(UNIT_TAGS.STATUS))
        {
            cadData.getUnit(unitNum).setStatus((String) value);
        }
        else if (tag.equals(UNIT_TAGS.OOS))
        {
            cadData.getUnit(unitNum).setOos((String) value);
        }
        else if (tag.equals(UNIT_TAGS.TYPE))
        {
            cadData.getUnit(unitNum).setType((String) value);
        }
        else if (tag.equals(UNIT_TAGS.CURR_LOC))
        {
            cadData.getUnit(unitNum).setCurrentLocation((String) value);
        }
        else if (tag.equals(UNIT_TAGS.DESTINATION))
        {
            cadData.getUnit(unitNum).setDestination((String) value);
        }
        else if (tag.equals(UNIT_TAGS.MISC_INFO))
        {
            cadData.getUnit(unitNum).setMisc((String) value);
        }
        else if (tag.equals(UNIT_TAGS.STACK))
        {
            cadData.getUnit(unitNum).setStack((String) value);
        }
        else if (tag.equals(UNIT_TAGS.AREA))
        {
            cadData.getUnit(unitNum).setArea((String) value);
        }
        else if (tag.equals(UNIT_TAGS.OFFICER))
        {
            cadData.getUnit(unitNum).setOfficer((String) value);
        }
        else if (tag.equals(UNIT_TAGS.BADGE_NUM))
        {
            cadData.getUnit(unitNum).setBadge((String) value);
        }
        else if (tag.equals(UNIT_TAGS.UNIT_STATUS))
        {
            cadData.getUnit(unitNum).setUnitStatus((UnitStatusEnums) value);
        }
        else if (tag.equals(UNIT_TAGS.OFFICE))
        {
            cadData.getUnit(unitNum).setOffice((String) value);
        }
        else if (tag.equals(UNIT_TAGS.P))
        {
            cadData.getUnit(unitNum).setP((String) value);
        }
        else if (tag.equals(UNIT_TAGS.AGY))
        {
            cadData.getUnit(unitNum).setAgy((String) value);
        }
        else if (tag.equals(UNIT_TAGS.ALIAS))
        {
            cadData.getUnit(unitNum).setAlias((String) value);
        }
        else
        {
            throw new RemoteException("Wrong Enum sent into Coordinator.setCadDataUnitValue");
        }
    }

    /**
     * Assigns a unit to the specified incident.
     *
     * @param unitNum the unitNum to look up
     * @param id the incident id that this unit is assigned to.
     * @throws RemoteException
     */
    public void setCadDataUnitAssignedId(String unitNum, int id) throws RemoteException
    {
        cadData.getUnit(unitNum).setAssignedIncidentId(id);
    }

    /**
     * Adds a unit to the incident's list of assigned units.
     *
     * @param incidentId the incident
     * @param assignedUnitNum the unit that's been assigned to the incident
     * @throws RemoteException
     */
    public void addCadDataIncidentAssignedUnitNum(int incidentId, String assignedUnitNum) throws RemoteException
    {
        cadData.getIncident(incidentId).addAssignedUnitNum(assignedUnitNum);
    }

    /**
     * Sets the specified incident to the specified status.
     *
     * @param incidentId the incident
     * @param status the status of the incident
     * @throws RemoteException
     */
    public void setCadDataIncidentStatus(int incidentId, IncidentEnums status) throws RemoteException
    {
        cadData.getIncident(incidentId).setIncidentStatus(status);
    }

    /**
     * Returns a LinkedList containing entries that match the search string.
     *
     * @param search the string entry to be searched
     * @return linked list of CardfileDataObjects matching search
     */
    public LinkedList<CardfileDataObject> getSearchList(String search) throws RemoteException
    {
        return cardfileData.getSearchList(search);
    }

    /**
     * Updates the server database so clients can view additional informations
     * as events complete
     *
     * @param incidentNumber the incident in which the event occurred
     * @return completedEvent IncidentEvent with information to be added to
     * server database
     */
    public void updateIncidentInGUI(Integer incidentNumber, IncidentEvent completedEvent)
    {
        updateDetailsInGUI(incidentNumber, completedEvent);
        updateUnitsInGUI(incidentNumber, completedEvent);
    }

    /**
     * Updates the server database so clients can view details as events
     * complete
     *
     * @param incidentNumber the incident in which the event occurred
     * @return completedEvent IncidentEvent with details to be added to server
     * database
     */
    public void updateDetailsInGUI(Integer incidentNumber, IncidentEvent completedEvent)
    {
        DateFormat dateFormat = new SimpleDateFormat("MM/dd/yyyy");
        DateFormat timeFormat = new SimpleDateFormat("HH:mm:ss");
        for (int i = 0; i < completedEvent.eventInfo.getDetails().size(); i++)
        {
            String[] fields =
            {
                dateFormat.format(new Date()),
                timeFormat.format(new Date()),
                "", "", completedEvent.eventInfo.getDetails().elementAt(i).details
            };

            try
            {
                addCadDataIncidentTable(INC_TABLE.COMMENTS_NOTES, incidentNumber, fields);
            } catch (RemoteException e)
            {
                e.printStackTrace();
            }
        }
    }

    /**
     * Updates the server database so clients can view unit updates as events
     * complete
     *
     * @param incidentNumber the incident in which the event occurred
     * @return completedEvent IncidentEvent with unit updates to be added to
     * server database
     */
    public void updateUnitsInGUI(Integer incidentNumber, IncidentEvent completedEvent)
    {
        for (int i = 0; i < completedEvent.eventInfo.getUnits().size(); i++)
        {
            IncidentInquiryUnitsAssigned unit = completedEvent.eventInfo.getUnits().get(i);
            if (unit.statusType.equals("ENRT"))
            {
                cadData.unitAssignedToIncident(unit.beat, incidentNumber, unit.isPrimary);
            }
            else if (unit.statusType.equals("1097"))
            {
                cadData.unitArrivedAtIncidentScene(unit.beat, incidentNumber, unit.isPrimary);
            }
            else if (unit.statusType.equals("1098"))
            {
                cadData.unitAvailable(unit.beat);
            }
        }
    }

    /**
     * Sets the specified incidentNumber to viewable in the GUI.
     *
     * @param incidentNumber the number of the Incident started
     */
    public void incidentStartedInGUI(Integer incidentNumber)
    {
        Date date = new Date();
        DateFormat dateFormat = new SimpleDateFormat("MM/dd/yyyy HH:mm:ss");
        cadData.getIncident(incidentNumber).setLogTime(dateFormat.format(date));
    }
}
