ingo@2702: package de.intevation.flys.artifacts.model;
ingo@2702: 
sascha@3777: import de.intevation.artifacts.Artifact;
ingo@2702: 
sascha@3777: import de.intevation.flys.artifacts.access.FlowVelocityAccess;
sascha@3777: 
ingo@2702: import de.intevation.flys.model.DischargeZone;
ingo@2702: import de.intevation.flys.model.FlowVelocityModel;
ingo@2702: import de.intevation.flys.model.FlowVelocityModelValue;
teichmann@5323: 
teichmann@5323: import java.util.ArrayList;
teichmann@5323: import java.util.Collections;
teichmann@5323: import java.util.List;
ingo@2702: 
sascha@3777: import org.apache.log4j.Logger;
ingo@2702: 
ingo@2702: 
felix@4483: /** Calculate flow velocity. */
ingo@2702: public class FlowVelocityCalculation extends Calculation {
ingo@2702: 
felix@4483:     /** Own logger. */
ingo@2702:     private static final Logger logger =
ingo@2702:         Logger.getLogger(FlowVelocityCalculation.class);
sascha@3232: 
sascha@3232: 
ingo@3230:     public CalculationResult calculate(FlowVelocityAccess access) {
ingo@2702:         logger.info("FlowVelocityCalculation.calculate");
sascha@3232: 
ingo@3230:         int[] mainIds  = access.getMainChannels();
ingo@3230:         int[] totalIds = access.getTotalChannels();
ingo@2702: 
ingo@2702:         if (logger.isDebugEnabled()) {
sascha@3258:             Artifact a = access.getArtifact();
ingo@3230:             logger.debug("Artifact '" + a.identifier() + "' contains:");
ingo@2702:             if (mainIds != null) {
ingo@2702:                 logger.debug("   " + mainIds.length + " main channel ids");
ingo@2702:             }
ingo@2702: 
ingo@2702:             if (totalIds != null) {
ingo@2702:                 logger.debug("   " + totalIds.length + " total channel ids");
ingo@2702:             }
ingo@2702:         }
ingo@2702: 
ingo@2702:         List<DischargeZone>     zones  = getDischargeZones(mainIds, totalIds);
ingo@3230:         List<FlowVelocityModel> models = getFlowVelocityModels(access, zones);
ingo@2702: 
ingo@3230:         return buildCalculationResult(access, models);
ingo@2702:     }
ingo@2702: 
ingo@2702: 
ingo@2702:     protected List<DischargeZone> getDischargeZones(
ingo@2702:         int[] mainIds,
ingo@2702:         int[] totalIds
ingo@2702:     ) {
ingo@2702:         List<DischargeZone> zones = new ArrayList<DischargeZone>();
ingo@2702: 
ingo@2702:         if (mainIds != null) {
ingo@2702:             for (int id: mainIds) {
ingo@2702:                 DischargeZone zone = DischargeZone.getDischargeZoneById(id);
rrenkert@4623:                 zone.putType("main");
ingo@2702: 
ingo@2702:                 if (zone != null) {
ingo@2702:                     zones.add(zone);
ingo@2702:                 }
ingo@2702:             }
ingo@2702:         }
ingo@2702: 
ingo@2702:         if (totalIds != null) {
ingo@2702:             for (int id: totalIds) {
ingo@2702:                 DischargeZone zone = DischargeZone.getDischargeZoneById(id);
ingo@2702:                 if (zone != null) {
rrenkert@4623:                     int ndx = zones.indexOf(zone);
rrenkert@4623:                     if (zones.contains(zone) &&
rrenkert@4623:                         zones.get(ndx).fetchType().equals("main")) {
rrenkert@4623:                         zone.putType("main_total");
rrenkert@4623:                     }
rrenkert@4623:                     else {
rrenkert@4623:                         zone.putType("total");
rrenkert@4623:                         zones.add(zone);
rrenkert@4623:                     }
ingo@2702:                 }
ingo@2702:             }
ingo@2702:         }
ingo@2702: 
ingo@2702:         return zones;
ingo@2702:     }
ingo@2702: 
ingo@2702: 
ingo@2702:     protected List<FlowVelocityModel> getFlowVelocityModels(
sascha@3258:         FlowVelocityAccess  access,
ingo@2702:         List<DischargeZone> zones
ingo@2702:     ) {
sascha@3777:         String riverName = access.getRiver();
sascha@3777:         if (riverName == null) {
sascha@3777:             logger.warn("No river name found");
sascha@3777:             return Collections.<FlowVelocityModel>emptyList();
sascha@3777:         }
sascha@3777: 
ingo@2702:         List<FlowVelocityModel> models = new ArrayList<FlowVelocityModel>();
ingo@2702: 
ingo@2702:         for (DischargeZone zone: zones) {
teichmann@5323:             List<FlowVelocityModel> model = FlowVelocityModel.getModels(zone);
teichmann@5323:             models.addAll(model);
ingo@2702:         }
ingo@2702: 
ingo@2702:         return models;
ingo@2702:     }
ingo@2702: 
ingo@2702: 
ingo@2702:     protected void prepareData(
ingo@2702:         FlowVelocityData  data,
ingo@2702:         FlowVelocityModel model,
ingo@2702:         double kmLo,
ingo@2702:         double kmHi
ingo@2702:     ) {
ingo@2702:         List<FlowVelocityModelValue> values =
ingo@2702:             FlowVelocityModelValue.getValues(model, kmLo, kmHi);
ingo@2702: 
ingo@2702:         logger.debug("Found " + values.size() + " values for model.");
ingo@2702: 
ingo@2702:         for (FlowVelocityModelValue value: values) {
ingo@2702:             data.addKM(value.getStation().doubleValue());
ingo@2702:             data.addQ(value.getQ().doubleValue());
ingo@2702:             data.addVTotal(value.getTotalChannel().doubleValue());
ingo@2702:             data.addVMain(value.getMainChannel().doubleValue());
ingo@2702:             data.addTauMain(value.getShearStress().doubleValue());
ingo@2702:         }
ingo@2702: 
ingo@2702:         DischargeZone zone = model.getDischargeZone();
ingo@2702:         String        lo   = zone.getLowerDischarge();
ingo@2702:         String        hi   = zone.getUpperDischarge();
ingo@2702: 
rrenkert@4623:         data.setType(zone.fetchType());
ingo@2702:         if (lo.equals(hi)) {
ingo@2702:             data.setZone(lo);
ingo@2702:         }
ingo@2702:         else {
ingo@2702:             data.setZone(lo + " - " + hi);
ingo@2702:         }
ingo@2702:     }
ingo@2702: 
ingo@2702: 
ingo@2702:     protected CalculationResult buildCalculationResult(
felix@4433:         FlowVelocityAccess         access,
ingo@2702:         List<FlowVelocityModel> models
ingo@2702:     ) {
ingo@3230:         double kmLo = access.getLowerKM();
ingo@3230:         double kmHi = access.getUpperKM();
ingo@2702: 
ingo@2702:         logger.debug("Prepare data for km range: " + kmLo + " - " + kmHi);
ingo@2702: 
ingo@2702:         FlowVelocityData[] data = new FlowVelocityData[models.size()];
ingo@2702:         for (int i = 0, n = models.size(); i < n; i++) {
ingo@2702:             FlowVelocityData d = new FlowVelocityData();
ingo@2702: 
ingo@2702:             prepareData(d, models.get(i), kmLo, kmHi);
ingo@2702: 
ingo@2702:             data[i] = d;
ingo@2702:         }
ingo@2702: 
ingo@2702:         logger.debug("Calculation contains " + data.length + " data items.");
ingo@2702: 
ingo@2702:         return new CalculationResult(data, this);
ingo@2702:     }
ingo@2702: }
ingo@2702: // vim:set ts=4 sw=4 si et sta sts=4 fenc=utf-8 :