]> gerrit.simantics Code Review - simantics/district.git/blobdiff - org.simantics.district.region/src/org/simantics/district/region/DiagramRegions.java
Add initial version of regions to source control
[simantics/district.git] / org.simantics.district.region / src / org / simantics / district / region / DiagramRegions.java
diff --git a/org.simantics.district.region/src/org/simantics/district/region/DiagramRegions.java b/org.simantics.district.region/src/org/simantics/district/region/DiagramRegions.java
new file mode 100644 (file)
index 0000000..57f31ae
--- /dev/null
@@ -0,0 +1,175 @@
+package org.simantics.district.region;
+
+import java.awt.Shape;
+import java.awt.geom.FlatteningPathIterator;
+import java.awt.geom.Path2D;
+import java.awt.geom.PathIterator;
+import java.util.ArrayList;
+import java.util.Arrays;
+import java.util.Collection;
+import java.util.HashSet;
+import java.util.List;
+import java.util.Set;
+import java.util.UUID;
+
+import org.simantics.Simantics;
+import org.simantics.databoard.Bindings;
+import org.simantics.db.ReadGraph;
+import org.simantics.db.Resource;
+import org.simantics.db.WriteGraph;
+import org.simantics.db.common.request.UniqueRead;
+import org.simantics.db.exception.DatabaseException;
+import org.simantics.db.layer0.QueryIndexUtils;
+import org.simantics.db.layer0.request.PossibleActiveModel;
+import org.simantics.db.layer0.util.RemoverUtil;
+import org.simantics.diagram.stubs.DiagramResource;
+import org.simantics.district.region.ontology.DiagramRegionsResource;
+import org.simantics.layer0.Layer0;
+import org.slf4j.Logger;
+import org.slf4j.LoggerFactory;
+
+public final class DiagramRegions {
+
+    private static final Logger LOGGER = LoggerFactory.getLogger(DiagramRegions.class);
+
+    public static Resource createRegionForDiagram(WriteGraph graph, Resource diagram, String label, double[] coordinates) throws DatabaseException {
+        if (coordinates == null || coordinates.length < 6 || coordinates.length % 2 != 0)
+            throw new IllegalArgumentException("Provided coordinates are not valid : " + Arrays.toString(coordinates));
+        Path2D path = new Path2D.Double();
+        double startX = coordinates[0];
+        double startY = coordinates[1];
+        path.moveTo(startX, startY);
+        for (int i = 2; i < coordinates.length; i++)
+            path.lineTo(coordinates[i], coordinates[++i]);
+
+        path.closePath(); // might not be needed
+        DiagramRegionsResource DRR = DiagramRegionsResource.getInstance(graph);
+        Layer0 L0 = Layer0.getInstance(graph);
+        Resource region = graph.newResource();
+        graph.claim(region, L0.InstanceOf, DRR.Region);
+        graph.claim(diagram, DRR.hasRegion, region);
+        graph.claim(region, DRR.regionOf, diagram);
+        graph.claimLiteral(region, L0.HasName, UUID.randomUUID().toString(), Bindings.STRING);
+        graph.claimLiteral(region, L0.HasLabel, label, Bindings.STRING);
+        graph.claimLiteral(region, DRR.Region_area, coordinates, Bindings.DOUBLE_ARRAY);
+        if (LOGGER.isDebugEnabled())
+            LOGGER.debug("Created region for diagram {} with label {} and area {}", diagram, label, Arrays.toString(coordinates));
+        return region;
+    }
+
+    public static void removeRegion(WriteGraph graph, Resource region) throws DatabaseException {
+        RemoverUtil.remove(graph, region);
+    }
+
+    public static class DiagramRegion {
+        
+        private Resource resource;
+        private String label;
+        private Shape shape;
+        
+        public DiagramRegion(Resource resource, String label, Shape coordinatesToShape) {
+            this.resource = resource;
+            this.label = label;
+            this.shape = coordinatesToShape;
+        }
+        
+        public Resource getResource() {
+            return resource;
+        }
+        
+        public String getLabel() {
+            return label;
+        }
+        
+        public Shape getShape() {
+            return shape;
+        }
+    }
+    
+    public static Collection<DiagramRegion> findRegions(ReadGraph graph, Resource model) throws DatabaseException {
+        List<Resource> diagrams = QueryIndexUtils.searchByType(graph, model, DiagramResource.getInstance(graph).Diagram);
+        Set<DiagramRegion> regions = new HashSet<>();
+        
+        Layer0 L0 = Layer0.getInstance(graph);
+        
+        for (Resource diagram : diagrams) {
+            Collection<Resource> region = graph.getObjects(diagram, DiagramRegionsResource.getInstance(graph).hasRegion);
+            for (Resource r : region) {
+                String label = graph.getRelatedValue(r, L0.HasLabel, Bindings.STRING);
+                Shape coordinatesToShape = DiagramRegions.coordinatesToShape(graph, r);
+                regions.add(new DiagramRegion(r, label, coordinatesToShape));
+            }
+        }
+        return regions;
+    }
+    
+    public static class DiagramRegionsRequest extends UniqueRead<Collection<DiagramRegion>> {
+
+        @Override
+        public Collection<DiagramRegion> perform(ReadGraph graph) throws DatabaseException {
+            return findRegions(graph, graph.syncRequest(new PossibleActiveModel(Simantics.getProjectResource())));
+        }
+    }
+
+    public static Shape coordinatesToShape(ReadGraph graph, Resource region) throws DatabaseException {
+        DiagramRegionsResource DRR = DiagramRegionsResource.getInstance(graph);
+        double[] coordinates = graph.getRelatedValue(region, DRR.Region_area, Bindings.DOUBLE_ARRAY);
+        Path2D path = new Path2D.Double();
+        double startX = coordinates[0];
+        double startY = coordinates[1];
+        path.moveTo(startX, startY);
+        for (int i = 2; i < coordinates.length; i++)
+            path.lineTo(coordinates[i], coordinates[++i]);
+
+        path.closePath(); // might not be needed
+        return path;
+    }
+
+    public static double[] shapeToCoordinates(Shape shape) {
+        PathIterator it = new FlatteningPathIterator(shape.getPathIterator(null), 1);
+        double points[] = new double[6];
+        double moveX = 0, moveY = 0;
+        double thisX = 0, thisY = 0;
+        int type = 0;
+
+        List<Double> coords = new ArrayList<>();
+        // float factor = 1;
+
+        while (!it.isDone()) {
+            type = it.currentSegment(points);
+            switch (type) {
+            case PathIterator.SEG_MOVETO:
+                moveX = points[0];
+                moveY = points[1];
+                coords.add(moveX);
+                coords.add(moveY);
+                break;
+
+            case PathIterator.SEG_CLOSE:
+                points[0] = moveX;
+                points[1] = moveY;
+                // Fall into....
+
+            case PathIterator.SEG_LINETO:
+                thisX = points[0];
+                thisY = points[1];
+                coords.add(thisX);
+                coords.add(thisY);
+                break;
+            }
+            it.next();
+        }
+        double[] finalCoords = new double[coords.size()];
+        for (int i = 0; i < coords.size(); i++) {
+            double d = coords.get(i);
+            finalCoords[i] = d;
+        }
+        return finalCoords;
+    }
+
+    public static Resource getDiagramForRegion(ReadGraph graph, Resource region) throws DatabaseException {
+        DiagramRegionsResource DRR = DiagramRegionsResource.getInstance(graph);
+        Resource diagram = graph.getSingleObject(region, DRR.regionOf);
+        return diagram;
+    }
+}