package edu.sc.seis.gee.task;

import java.util.Arrays;
import java.util.Map;
import java.util.StringTokenizer;
import edu.iris.Fissures.Location;
import edu.iris.Fissures.IfEvent.EventAccessOperations;
import edu.iris.Fissures.IfEvent.NoPreferredOrigin;
import edu.iris.Fissures.IfEvent.Origin;
import edu.iris.Fissures.IfNetwork.Channel;
import edu.iris.Fissures.IfNetwork.ChannelId;
import edu.iris.Fissures.IfNetwork.Site;
import edu.iris.Fissures.model.QuantityImpl;
import edu.iris.Fissures.model.UnitImpl;
import edu.sc.seis.TauP.Arrival;
import edu.sc.seis.TauP.SphericalCoords;
import edu.sc.seis.fissuresUtil.cache.EventUtil;
import edu.sc.seis.fissuresUtil.xml.DataSet;
import edu.sc.seis.fissuresUtil.xml.DataSetSeismogram;
import edu.sc.seis.gee.CommonAccess;
import edu.sc.seis.gee.configurator.ConfigurationException;

/**
 * TauPTask.java Created: Wed Jan 16 15:43:24 2002
 * 
 * @author <a href="mailto:">Philip Crotwell </a>
 * @version
 */
public class TauPTask implements Task {

    public void configure(Map params) throws ConfigurationException {
        this.params = params;
        if(params.containsKey("calculatorTitle")) {
            taup = new TauP((String)params.get("calculatorTitle"));
        } else {
            taup = new TauP("Earthquake Travel Time Calculator");
        }
        if(params.containsKey("phases")) {
            String phasesString = (String)params.get("phases");
            StringTokenizer phasesTok = new StringTokenizer(phasesString, ",");
            int tokens = phasesTok.countTokens();
            String[] phases = new String[tokens];
            for(int i = 0; i < tokens; i++) {
                phases[i] = phasesTok.nextToken();
            }
            taup.setSelectedPhases(phases);
        }
        if(params.containsKey("filter")) {
            String filterId = (String)params.get("filter");
            TaskAction filterAction = CommonAccess.getCommonAccess()
                    .getTaskAction(filterId);
            filter = (PhaseFilter)filterAction.getTask();
        }
    }

    public void invoke() {
        taup.show();
    }

    public Arrival[] getArrivals(DataSetSeismogram seis) {
        ChannelId chanId = seis.getRequestFilter().channel_id;
        DataSet ds = seis.getDataSet();
        Channel chan = ds.getChannel(chanId);
        EventAccessOperations event = ds.getEvent();
        return getArrivals(chan, event, filter);
    }

    public Arrival[] getArrivals(Channel chan, EventAccessOperations event) {
        return getArrivals(chan, event, filter);
    }

    public Arrival[] getArrivals(Channel chan,
                                 EventAccessOperations event,
                                 PhaseFilter filter) {
        Location eventLoc = EventUtil.extractOrigin(event).getLocation();
        Site site = chan.getSite();
        Arrival[] arrivals = null;
        arrivals = taup.calculate(SphericalCoords.distance(site.getLocation().latitude,
                                                           site.getLocation().longitude,
                                                           eventLoc.latitude,
                                                           eventLoc.longitude),
                                  ((QuantityImpl)eventLoc.depth).convertTo(UnitImpl.KILOMETER).value);
        if(filter != null) {
            arrivals = filter.filter(Arrays.asList(arrivals)).toArray(new Arrival[0]);
        }
        return arrivals;
    }

    public void setTauPListener(PhasePlotTask listener) {
        taup.setTauPListener(listener);
    }

    public void destroy() {}

    public TauP getTauP() {
        return taup;
    }

    protected TauP taup;

    private Map params;

    private PhaseFilter filter;
}// TauPTask
