X-Git-Url: https://gerrit.simantics.org/r/gitweb?a=blobdiff_plain;f=org.simantics.district.network%2Fsrc%2Forg%2Fsimantics%2Fdistrict%2Fnetwork%2FDistrictNetworkUtil.java;h=85ebd06c488ba27a1c4912dbd3eb40437a57eab1;hb=087d4a2f6c4ea1dbc9ed889ba7d612e9c5a86210;hp=ae73e56bc2119806cd816e069dc0732e2e489e7d;hpb=60c060751f037be8f1643656327799f70a3504b1;p=simantics%2Fdistrict.git diff --git a/org.simantics.district.network/src/org/simantics/district/network/DistrictNetworkUtil.java b/org.simantics.district.network/src/org/simantics/district/network/DistrictNetworkUtil.java index ae73e56b..85ebd06c 100644 --- a/org.simantics.district.network/src/org/simantics/district/network/DistrictNetworkUtil.java +++ b/org.simantics.district.network/src/org/simantics/district/network/DistrictNetworkUtil.java @@ -3,19 +3,30 @@ package org.simantics.district.network; import java.awt.geom.Rectangle2D; import java.util.ArrayList; import java.util.Collection; +import java.util.Collections; +import java.util.Comparator; +import java.util.HashSet; import java.util.Iterator; import java.util.List; +import java.util.Set; import java.util.stream.Collectors; import java.util.stream.Stream; +import org.simantics.Simantics; import org.simantics.databoard.Bindings; import org.simantics.datatypes.literal.RGB; import org.simantics.datatypes.literal.RGB.Integer; import org.simantics.db.ReadGraph; +import org.simantics.db.RequestProcessor; import org.simantics.db.Resource; import org.simantics.db.WriteGraph; +import org.simantics.db.common.NamedResource; import org.simantics.db.common.procedure.adapter.TransientCacheListener; +import org.simantics.db.common.request.BinaryRead; import org.simantics.db.common.request.IndexRoot; +import org.simantics.db.common.request.ObjectsWithType; +import org.simantics.db.common.request.PossibleChild; +import org.simantics.db.common.request.PossibleIndexRoot; import org.simantics.db.common.request.ResourceRead; import org.simantics.db.common.utils.OrderedSetUtils; import org.simantics.db.exception.BindingException; @@ -23,6 +34,8 @@ import org.simantics.db.exception.DatabaseException; import org.simantics.db.exception.ManyObjectsForFunctionalRelationException; import org.simantics.db.exception.ServiceException; import org.simantics.db.indexing.IndexUtils; +import org.simantics.db.layer0.QueryIndexUtils; +import org.simantics.db.layer0.request.PossibleActiveModel; import org.simantics.db.layer0.request.PossibleVariable; import org.simantics.db.layer0.variable.Variable; import org.simantics.diagram.stubs.DiagramResource; @@ -39,6 +52,9 @@ import org.simantics.operation.Layer0X; import org.slf4j.Logger; import org.slf4j.LoggerFactory; +import com.vividsolutions.jts.geom.Envelope; +import com.vividsolutions.jts.index.quadtree.Quadtree; + public class DistrictNetworkUtil { private static final Logger LOGGER = LoggerFactory.getLogger(DistrictNetworkUtil.class); @@ -386,4 +402,127 @@ public class DistrictNetworkUtil { } return results; } + + public static List nearbyResourceVertices(ReadGraph graph, Resource diagramResource, Resource vertex, Double padding) throws DatabaseException { + double halfPadding = padding / 2; + + Quadtree existingVertices = graph.syncRequest(new ExistingVerticesRead(diagramResource, halfPadding), TransientCacheListener.instance()); + double[] coords = graph.getRelatedValue(vertex, DiagramResource.getInstance(graph).HasLocation, Bindings.DOUBLE_ARRAY); + double x1 = coords[0] - halfPadding; + double y1= coords[1] - halfPadding; + double x2 = coords[0] + halfPadding; + double y2= coords[1] + halfPadding; + Envelope e = new Envelope(x1, x2, y1, y2); + + List result = existingVertices.query(e); + @SuppressWarnings("unchecked") + List vertices = (List) result; + + Rectangle2D vertexRectangle = new Rectangle2D.Double(coords[0] - halfPadding, coords[1] - halfPadding, padding, padding); + + // let's sort by distance + List sortedVertices = vertices.stream().filter(rv -> { + if (rv.vertex.equals(vertex)) + return false; + + Rectangle2D nearbyRectangle = new Rectangle2D.Double(rv.coords[0] - halfPadding, rv.coords[1] - halfPadding, padding, padding); + return vertexRectangle.intersects(nearbyRectangle); + }).sorted((o1, o2) -> { + double disto1 = Math.sqrt((Math.pow(coords[0] - o1.coords[0], 2) + (Math.pow(coords[1] - o1.coords[1], 2)))); + double disto2 = Math.sqrt((Math.pow(coords[0] - o2.coords[0], 2) + (Math.pow(coords[1] - o2.coords[1], 2)))); + + if (o1.vertex.getResourceId() == 2554883) { + System.err.println("here we are"); + } + + return Double.compare(disto1, disto2); + }).collect(Collectors.toList()); + return sortedVertices; + } + + public static List nearbyVertices(ReadGraph graph, Resource vertex, double padding) throws DatabaseException { + Resource diagramResource = graph.getSingleObject(vertex, Layer0.getInstance(graph).PartOf); + return nearbyResourceVertices(graph, diagramResource, vertex, padding) + .stream() + .map(rv -> rv.vertex) + .collect(Collectors.toList()); + } + + public static Quadtree existingVertices(Resource diagramResource, Double padding) throws DatabaseException { + Quadtree vv = Simantics.getSession().syncRequest(new ExistingVerticesRead(diagramResource, padding)); + return vv; + } + + public static class ExistingVerticesRead extends BinaryRead { + + public ExistingVerticesRead(Resource diagramResource, Double padding) { + super(diagramResource, padding); + } + + @Override + public Quadtree perform(ReadGraph graph) throws DatabaseException { + Collection vertices = graph.syncRequest(new ObjectsWithType(parameter, Layer0.getInstance(graph).ConsistsOf, DistrictNetworkResource.getInstance(graph).Vertex)); + Quadtree vv = new Quadtree(); + for (Resource vertex : vertices) { + double[] coords = graph.getRelatedValue2(vertex, DiagramResource.getInstance(graph).HasLocation, Bindings.DOUBLE_ARRAY); + double x1 = coords[0] - parameter2; + double y1= coords[1] - parameter2; + double x2 = coords[0] + parameter2; + double y2= coords[1] + parameter2; + Envelope e = new Envelope(x1, x2, y1, y2); + vv.insert(e, new ResourceVertex(vertex, coords, true)); + } + return vv; + } + } + + public static class DistrictComponentListRequest extends ResourceRead> { + protected DistrictComponentListRequest(Resource model) { + super(model); + } + + @Override + public List perform(ReadGraph graph) throws DatabaseException { + Layer0 L0 = Layer0.getInstance(graph); + DistrictNetworkResource DN = DistrictNetworkResource.getInstance(graph); + + Resource model = this.resource; + + Set componentTypes = new HashSet<>(); + Collection mappings = QueryIndexUtils.searchByType(graph, model, DN.Mapping_Base); + for (Resource r : mappings) { + String componentType = graph.getPossibleRelatedValue2(r, DN.Mapping_ComponentType); + if (componentType != null) { + Resource root = graph.syncRequest(new PossibleIndexRoot(r)); + if (root != null) { + Resource type = graph.syncRequest(new PossibleChild(root, componentType)); + if (type != null) + componentTypes.add(type); + } + } + } + + List result = new ArrayList(componentTypes.size()); + for (Resource r : componentTypes) { + String name = graph.getPossibleRelatedValue(r, L0.HasName); + result.add(new NamedResource(name, r)); + } + + result.sort(Comparator.comparing(NamedResource::getName)); + return result; + } + } + + public static List getDistrictComponents() throws DatabaseException { + return getDistrictComponents(Simantics.getSession()); + } + + public static List getDistrictComponents(RequestProcessor session) throws DatabaseException { + Resource model = session.syncRequest(new PossibleActiveModel(Simantics.getProjectResource())); + if (model == null) + return Collections.emptyList(); + + return session.syncRequest(new DistrictComponentListRequest(model), TransientCacheListener.instance()); + } + }