teichmann@5863: /* Copyright (C) 2011, 2012, 2013 by Bundesanstalt für Gewässerkunde teichmann@5863: * Software engineering by Intevation GmbH teichmann@5863: * teichmann@5994: * This file is Free Software under the GNU AGPL (>=v3) teichmann@5863: * and comes with ABSOLUTELY NO WARRANTY! Check out the teichmann@5994: * documentation coming with Dive4Elements River for details. teichmann@5863: */ teichmann@5863: teichmann@5831: package org.dive4elements.river.artifacts.states; ingo@1172: ingo@1178: import org.apache.log4j.Logger; ingo@1178: ingo@1180: import org.w3c.dom.Element; ingo@1180: teichmann@5831: import org.dive4elements.artifacts.Artifact; teichmann@5831: import org.dive4elements.artifacts.CallContext; ingo@1178: teichmann@5831: import org.dive4elements.artifactdatabase.data.DefaultStateData; teichmann@5831: import org.dive4elements.artifactdatabase.data.StateData; ingo@1180: teichmann@5831: import org.dive4elements.artifacts.common.utils.XMLUtils.ElementCreator; teichmann@5831: teichmann@5867: import org.dive4elements.river.artifacts.D4EArtifact; teichmann@5831: import org.dive4elements.river.artifacts.model.CalculationResult; teichmann@5831: import org.dive4elements.river.artifacts.model.WQKms; teichmann@5831: import org.dive4elements.river.artifacts.model.extreme.ExtremeResult; felix@7636: import org.dive4elements.river.artifacts.model.fixings.FixRealizingResult; teichmann@5831: import org.dive4elements.river.artifacts.resources.Resources; teichmann@5865: import org.dive4elements.river.utils.RiverUtils; teichmann@5831: import org.dive4elements.river.utils.StringUtil; ingo@1178: ingo@1178: ingo@1172: /** ingo@1172: * @author Ingo Weinzierl ingo@1172: */ ingo@1172: public class WaterlevelSelectState extends DefaultState { ingo@1172: ingo@1178: private static final Logger logger = ingo@1178: Logger.getLogger(WaterlevelSelectState.class); ingo@1178: ingo@1178: public static final String SPLIT_CHAR = ";"; ingo@1178: ingo@1180: public static final String WINFO_WSP_STATE_ID = "state.winfo.waterlevel"; ingo@1180: ingo@1180: public static final String I18N_STATIC_KEY = "wsp.selected.string"; ingo@1180: ingo@1178: ingo@1172: @Override ingo@1172: protected String getUIProvider() { ingo@1172: return "wsp_datacage_panel"; ingo@1172: } ingo@1178: ingo@1178: felix@1655: /** felix@1655: * @param flys ignored felix@1655: * @param cc ignrored felix@1655: */ ingo@1178: @Override ingo@1178: public StateData transform( teichmann@5867: D4EArtifact flys, ingo@1178: CallContext cc, ingo@2205: StateData stateData, ingo@1178: String name, ingo@1178: String val ingo@1178: ) { ingo@1178: if (!isValueValid(val)) { ingo@1178: logger.error("The given input string is not valid: '" + val + "'"); ingo@1178: return null; ingo@1178: } ingo@1178: felix@1655: return new DefaultStateData(name, null, null, StringUtil.unbracket(val)); ingo@1178: } ingo@1178: ingo@1178: ingo@1178: @Override ingo@1178: public boolean validate(Artifact artifact) ingo@1178: throws IllegalArgumentException ingo@1178: { teichmann@5867: D4EArtifact flys = (D4EArtifact) artifact; ingo@1178: ingo@1178: StateData data = flys.getData("wsp"); ingo@1178: ingo@1178: if (data == null) { ingo@1178: throw new IllegalArgumentException("WSP is empty"); ingo@1178: } ingo@1178: ingo@1178: return true; ingo@1178: } ingo@1178: ingo@1178: ingo@1180: @Override ingo@1180: protected Element createStaticData( teichmann@5867: D4EArtifact flys, ingo@1180: ElementCreator creator, ingo@1180: CallContext cc, ingo@1180: String name, ingo@1180: String value, ingo@1180: String type ingo@1180: ) { ingo@1180: Element dataElement = creator.create("data"); ingo@1180: creator.addAttr(dataElement, "name", name, true); ingo@1180: creator.addAttr(dataElement, "type", type, true); ingo@1180: ingo@1180: Element itemElement = creator.create("item"); ingo@1180: creator.addAttr(itemElement, "value", value, true); ingo@1180: ingo@1180: String[] labels = getLabels(cc, value); ingo@1180: Object[] obj = new Object[] { labels[0] }; ingo@1180: ingo@1180: String attrValue = Resources.getMsg( ingo@1180: cc.getMeta(), I18N_STATIC_KEY, I18N_STATIC_KEY, obj); ingo@1180: ingo@1180: creator.addAttr(itemElement, "label", attrValue, true); ingo@1180: dataElement.appendChild(itemElement); ingo@1180: ingo@1180: return dataElement; ingo@1180: } ingo@1180: ingo@1180: felix@1655: /** felix@1655: * Get name to display for selected watelerlevel (for example "Q=123") sascha@3076: * from the CalculationResult. felix@1655: */ ingo@1180: public static String[] getLabels(CallContext cc, String value) { ingo@1180: String[] parts = value.split(SPLIT_CHAR); ingo@1180: teichmann@5867: D4EArtifact artifact = RiverUtils.getArtifact(parts[0], cc); ingo@1180: felix@7571: Object rawData = artifact.compute( ingo@1180: cc, ingo@1180: null, felix@7571: //WINFO_WSP_STATE_ID, felix@7571: artifact.getCurrentStateId(), ingo@1180: ComputeType.ADVANCE, ingo@1180: false); ingo@1180: felix@5415: WQKms[] wqkms; felix@5415: felix@7571: // TODO issue1020: Fetch cases in which only WKms or felix@7571: // other weird stuff arrives. felix@7571: if (rawData instanceof CalculationResult) { felix@7571: CalculationResult calcResult = (CalculationResult) rawData; felix@7571: if (calcResult.getData() instanceof ExtremeResult) { felix@7571: wqkms = ((ExtremeResult) calcResult.getData()).getWQKms(); felix@7571: } felix@7636: else if (calcResult.getData() instanceof FixRealizingResult) { felix@7636: wqkms = ((FixRealizingResult) calcResult.getData()).getWQKms(); felix@7636: } felix@7571: else { felix@7571: wqkms = (WQKms[]) calcResult.getData(); felix@7571: } felix@7571: } felix@7571: else if (rawData instanceof WQKms) { felix@7571: wqkms = new WQKms[] {(WQKms) rawData}; felix@7571: } felix@7571: else if (rawData instanceof WQKms[]) { felix@7571: wqkms = (WQKms[]) rawData; felix@5415: } felix@5415: else { felix@7571: logger.error("Do not know how to handle " + rawData.getClass()); felix@7571: wqkms = null; felix@5415: } ingo@1180: ingo@1180: int idx = -1; ingo@1180: try { ingo@1180: idx = Integer.parseInt(parts[2]); felix@6016: String name = wqkms[idx].getName(); ingo@1180: felix@6016: return new String[] { StringUtil.wWrap(name) }; felix@6016: } felix@6016: catch (NumberFormatException nfe) { /* do nothing */ felix@6016: logger.error("Cannot get label for " + value + " (" + parts[2] + ")"); felix@6016: return new String[] {""}; felix@6016: } ingo@1180: } ingo@1180: ingo@1180: ingo@1178: /** ingo@1178: * Validates the given String. A valid string for this state requires the ingo@1178: * format: "UUID;FACETNAME;FACETINDEX". ingo@1178: * ingo@1178: * @param value The string value requires validation. ingo@1178: * ingo@1178: * @return true, if the string applies the specified format, otherwise ingo@1178: * false. ingo@1178: */ ingo@1178: public static boolean isValueValid(String value) { ingo@1178: logger.debug("Validate string: '" + value + "'"); ingo@1178: felix@1655: value = StringUtil.unbracket(value); ingo@1178: ingo@1178: logger.debug("Validate substring: '" + value + "'"); ingo@1178: ingo@1178: if (value == null || value.length() == 0) { ingo@1178: return false; ingo@1178: } ingo@1178: ingo@1178: String[] parts = value.split(SPLIT_CHAR); ingo@1178: ingo@1178: if (parts == null || parts.length < 3) { ingo@1178: return false; ingo@1178: } ingo@1178: ingo@1178: if (parts[0] == null || parts[0].length() == 0) { ingo@1178: return false; ingo@1178: } ingo@1178: ingo@1178: if (parts[1] == null || parts[1].length() == 0) { ingo@1178: return false; ingo@1178: } ingo@1178: ingo@1178: try { ingo@1178: Integer.parseInt(parts[2]); ingo@1178: } ingo@1178: catch (NumberFormatException nfe) { ingo@1178: logger.error("Index is not a valid integer!", nfe); ingo@1178: } ingo@1178: ingo@1178: return true; ingo@1178: } ingo@1172: } ingo@1172: // vim:set ts=4 sw=4 si et sta sts=4 fenc=utf-8 :