diff artifacts/src/main/java/org/dive4elements/river/artifacts/model/CrossSectionWaterLineFacet.java @ 9425:3f49835a00c3

Extended CrossSectionFacet so it may fetch different data from within the artifact result. Also allows to have acces to the potentially already computed artifact result via its normal computation cache.
author gernotbelger
date Fri, 17 Aug 2018 15:31:02 +0200
parents 5e38e2924c07
children bd5f5d2220fa
line wrap: on
line diff
--- a/artifacts/src/main/java/org/dive4elements/river/artifacts/model/CrossSectionWaterLineFacet.java	Fri Aug 17 14:29:05 2018 +0200
+++ b/artifacts/src/main/java/org/dive4elements/river/artifacts/model/CrossSectionWaterLineFacet.java	Fri Aug 17 15:31:02 2018 +0200
@@ -8,76 +8,85 @@
 
 package org.dive4elements.river.artifacts.model;
 
-import org.apache.log4j.Logger;
-
+import java.io.Serializable;
 import java.util.List;
 
+import org.apache.log4j.Logger;
+import org.dive4elements.artifactdatabase.state.Facet;
 import org.dive4elements.artifacts.Artifact;
 import org.dive4elements.artifacts.CallContext;
 import org.dive4elements.artifacts.DataProvider;
-
-import org.dive4elements.artifactdatabase.state.Facet;
-
 import org.dive4elements.river.artifacts.WaterLineArtifact;
-
+import org.dive4elements.river.artifacts.geom.Lines;
+import org.dive4elements.river.artifacts.geom.Lines.LineData;
+import org.dive4elements.river.artifacts.states.DefaultState.ComputeType;
 import org.dive4elements.river.model.FastCrossSectionLine;
 
-import org.dive4elements.river.artifacts.geom.Lines;
-
-
 /**
  * Facet for Waterlines in Cross Sections.
  */
-public class CrossSectionWaterLineFacet
-extends      BlackboardDataFacet
-implements   FacetTypes {
+public class CrossSectionWaterLineFacet extends DataFacet implements FacetTypes {
+
+    private static final LineData NO_LINE_DATA = new Lines.LineData(new double[][] {}, 0d, 0d);
+
+    private static final long serialVersionUID = 1L;
 
     /** Private log to use. */
-    private static Logger log =
-        Logger.getLogger(CrossSectionWaterLineFacet.class);
+    private static Logger log = Logger.getLogger(CrossSectionWaterLineFacet.class);
 
+    private final Serializable waterLineIndex;
 
     /** Trivial constructor, set (maybe localized) description. */
-    public CrossSectionWaterLineFacet(int idx, String description) {
-        super(idx, CROSS_SECTION_WATER_LINE, description);
+    public CrossSectionWaterLineFacet(final int idx, final String description, final ComputeType type, final String hash, final String stateId,
+            final Serializable waterLineIndex) {
+        this(idx, CROSS_SECTION_WATER_LINE, description, type, hash, stateId, waterLineIndex);
     }
 
-
     /**
      * Trivial constructor, set (maybe localized) description.
-     * @param idx Index of this facet.
-     * @param name 'type' of this facet.
-     * @param description (maybe) localized user-visible description.
+     *
+     * @param facetIndex
+     *            Index of this facet.
+     * @param waterLineIndex
+     *            Determines which water-line the artifact will return. Depends on the implementation of the artifact.
+     *            Is serializable because this class is, must be immutable because only the reference is copied in
+     *            'deepCopy'
+     * @param name
+     *            'type' of this facet.
+     * @param description
+     *            (maybe) localized user-visible description.
      */
-    public CrossSectionWaterLineFacet(
-        int idx,
-        String name,
-        String description
-    ) {
-        super(idx, name, description);
+    public CrossSectionWaterLineFacet(final int facetIndex, final String name, final String description, final ComputeType type, final String hash,
+            final String stateId, final Serializable waterLineIndex) {
+        super(facetIndex, name, description, type, hash, stateId);
+
+        this.waterLineIndex = waterLineIndex;
     }
 
-
     /**
      * Gets waterline (crossed with cross section) of waterlevel.
+     * FIXME: the cross section facets delgate fetching the data to the artifact, which in turn (in most cases) re-calculate
+     * the artifact on every call....
+     * Instead this should work like other facets that rely on the hashed computation.
      */
-    public Object getData(Artifact artifact, CallContext context) {
+    @Override
+    public Object getData(final Artifact artifact, final CallContext context) {
         log.debug("Get data for cross section water line");
 
-        List<DataProvider> providers = context.
-            getDataProvider(CrossSectionFacet.BLACKBOARD_CS_MASTER_DATA);
+        final List<DataProvider> providers = context.getDataProvider(CrossSectionFacet.BLACKBOARD_CS_MASTER_DATA);
         if (providers.size() < 1) {
             log.warn("Could not find Cross-Section data provider.");
-            return new Lines.LineData(new double[][] {}, 0d, 0d);
+            return NO_LINE_DATA;
         }
 
-        Object crossSection = providers.get(0)
-            .provideData(CrossSectionFacet.BLACKBOARD_CS_MASTER_DATA,
-                null, context);
-        Object nextKm = providers.get(0).
-            provideData(CrossSectionFacet.BLACKBOARD_CS_NEXT_KM, null, context);
-        Object prevKm = providers.get(0).
-            provideData(CrossSectionFacet.BLACKBOARD_CS_PREV_KM, null, context);
+        final DataProvider dataProvider = providers.get(0);
+
+        final FastCrossSectionLine crossSection = (FastCrossSectionLine) dataProvider.provideData(CrossSectionFacet.BLACKBOARD_CS_MASTER_DATA, null, context);
+        if (crossSection == null)
+            return NO_LINE_DATA;
+
+        Object nextKm = dataProvider.provideData(CrossSectionFacet.BLACKBOARD_CS_NEXT_KM, null, context);
+        Object prevKm = dataProvider.provideData(CrossSectionFacet.BLACKBOARD_CS_PREV_KM, null, context);
         if (prevKm == null)
             prevKm = new Double(-1d);
         if (nextKm == null)
@@ -85,29 +94,28 @@
 
         if (!(artifact instanceof WaterLineArtifact)) {
             log.error("CrossSectionWaterLineFacet needs WaterLineArtifact");
-            return new Lines.LineData(new double[][] {}, 0d,0d);
+            return NO_LINE_DATA;
         }
-        WaterLineArtifact lineArtifact = (WaterLineArtifact) artifact;
 
-        if (crossSection != null) {
-            return lineArtifact.getWaterLines(this.getIndex(),
-                (FastCrossSectionLine) crossSection, (Double) nextKm,
-                (Double) prevKm, context);
-        }
-        else {
-            return new Lines.LineData(new double[][] {}, 0d,0d);
-        }
+        final WaterLineArtifact lineArtifact = (WaterLineArtifact) artifact;
+
+        final double currentKm = crossSection.getKm();
+
+        final double waterLevel = lineArtifact.getWaterLevel(this.type, this.hash, this.stateId, currentKm, this.waterLineIndex, (Double) nextKm,
+                (Double) prevKm,
+                context);
+        if (Double.isNaN(waterLevel))
+            return NO_LINE_DATA;
+
+        return Lines.createWaterLines(crossSection.getPoints(), waterLevel);
     }
 
-
     /** Do a deep copy. */
     @Override
     public Facet deepCopy() {
-        CrossSectionWaterLineFacet copy = new CrossSectionWaterLineFacet(
-            this.getIndex(),
-            this.description);
+        final CrossSectionWaterLineFacet copy = new CrossSectionWaterLineFacet(this.getIndex(), this.name, this.description, this.type, this.hash, this.stateId,
+                this.waterLineIndex);
         copy.set(this);
         return copy;
     }
-}
-// vim:set ts=4 sw=4 si et sta sts=4 fenc=utf8 :
+}
\ No newline at end of file

http://dive4elements.wald.intevation.org