X-Git-Url: https://gerrit.simantics.org/r/gitweb?a=blobdiff_plain;f=bundles%2Forg.simantics.diagram%2Fsrc%2Forg%2Fsimantics%2Fdiagram%2Fsynchronization%2Fgraph%2FCopyAdvisorUtil.java;h=bbf9a8e5b23d2134f536bacb21cae26d058e815e;hb=fc9dd64c8ee2b35fb665f6979a80edf08bf09c1f;hp=60d4c56aeaa54d9c5d0559dcea7b189d188e6a06;hpb=0ae2b770234dfc3cbb18bd38f324125cf0faca07;p=simantics%2Fplatform.git diff --git a/bundles/org.simantics.diagram/src/org/simantics/diagram/synchronization/graph/CopyAdvisorUtil.java b/bundles/org.simantics.diagram/src/org/simantics/diagram/synchronization/graph/CopyAdvisorUtil.java index 60d4c56ae..bbf9a8e5b 100644 --- a/bundles/org.simantics.diagram/src/org/simantics/diagram/synchronization/graph/CopyAdvisorUtil.java +++ b/bundles/org.simantics.diagram/src/org/simantics/diagram/synchronization/graph/CopyAdvisorUtil.java @@ -11,11 +11,11 @@ *******************************************************************************/ package org.simantics.diagram.synchronization.graph; -import gnu.trove.map.hash.THashMap; - import java.util.Map; import java.util.Set; +import java.util.function.BiFunction; +import org.eclipse.core.runtime.NullProgressMonitor; import org.simantics.databoard.Bindings; import org.simantics.databoard.binding.Binding; import org.simantics.databoard.type.Datatype; @@ -46,6 +46,9 @@ import org.simantics.graph.representation.TransferableGraph1; import org.simantics.layer0.Layer0; import org.simantics.utils.datastructures.BinaryFunction; +import gnu.trove.map.hash.THashMap; +import gnu.trove.set.hash.THashSet; + /** * This class contains utility methods for the basic cut/copy operations * performed related to cut-copy-pasting diagram/configuration component and @@ -81,6 +84,15 @@ public class CopyAdvisorUtil { public static final boolean DEBUG_COPY = DebugPolicy.DEBUG_COPY_PASTE; + private static class Statement4 { + public final Statement stm; + public final Resource inverse; + public Statement4(Statement stm, Resource inverse) { + this.stm = stm; + this.inverse = inverse; + } + } + /** * @param context a synchronization context instance, such as * {@link GraphToDiagramSynchronizer} @@ -223,7 +235,7 @@ public class CopyAdvisorUtil { * @return the copied resource * @throws DatabaseException */ - public static Resource copy(WriteGraph graph, Resource source, BinaryFunction advisor) throws DatabaseException { + public static Resource copy(WriteGraph graph, Resource source, BiFunction advisor) throws DatabaseException { return copy(graph, source, 0, advisor, new THashMap()); } @@ -238,11 +250,11 @@ public class CopyAdvisorUtil { * @return * @throws DatabaseException */ - public static Resource copy(WriteGraph graph, Resource source, BinaryFunction advisor, Map copyMap) throws DatabaseException { + public static Resource copy(WriteGraph graph, Resource source, BiFunction advisor, Map copyMap) throws DatabaseException { return copy(graph, source, 0, advisor, copyMap); } - private static Resource copy(WriteGraph graph, Resource source, int level, BinaryFunction advisor, Map copyMap) throws DatabaseException { + private static Resource copy(WriteGraph graph, Resource source, int level, BiFunction advisor, Map copyMap) throws DatabaseException { if (DEBUG_COPY) System.out.println("[" + level + "] CopyAdvisorUtil.copy(" + NameUtils.getSafeName(graph, source) + ", advisor=" + advisor + ")"); @@ -320,7 +332,7 @@ public class CopyAdvisorUtil { } } else { if (advisor != null) { - Boolean result = advisor.call(graph, stm); + Boolean result = advisor.apply(graph, stm); if (Boolean.TRUE.equals(result)) { // Don't clone the object, just add relation to the same object. if (inverse != null) @@ -363,8 +375,10 @@ public class CopyAdvisorUtil { * @throws DatabaseException */ public static Resource copy2(WriteGraph graph, Resource source, - BinaryFunction advisor) throws DatabaseException { - return copy2(graph, source, 0, advisor, new THashMap()); + BiFunction advisor) + throws DatabaseException + { + return copy2(graph, source, advisor, new THashMap<>()); } /** @@ -379,13 +393,52 @@ public class CopyAdvisorUtil { * @throws DatabaseException */ public static Resource copy2(WriteGraph graph, Resource source, - BinaryFunction advisor, Map copyMap) - throws DatabaseException { - return copy2(graph, source, 0, advisor, copyMap); + BiFunction advisor, + Map copyMap) + throws DatabaseException + { + Set pendingStatements = new THashSet<>(); + Resource result = copy2(graph, source, 0, advisor, copyMap, pendingStatements); + postProcessStatements(graph, copyMap, pendingStatements); + return result; + } + + /** + * Post-process pending statement + * + * Rule: If both the subject and object of a pending source statement have + * been copied, then the pending statement should also be copied. + */ + private static void postProcessStatements( + WriteGraph graph, + Map copyMap, + Set pendingStatements) + throws DatabaseException + { + if (pendingStatements.isEmpty()) + return; + + if (DEBUG_COPY) + System.out.println("post processing " + pendingStatements.size() + " pending statements"); + for (Statement4 srcStm : pendingStatements) { + // At this point, it is certain that srcStm subject has been copied + // but test it anyway. + Resource subjectCopy = (Resource) copyMap.get(srcStm.stm.getSubject()); + Resource objectCopy = (Resource) copyMap.get(srcStm.stm.getObject()); + if (subjectCopy == null || objectCopy == null) { + if (DEBUG_COPY) + System.out.println("skipping pending statement: " + NameUtils.toString(graph, srcStm.stm)); + continue; + } + if (DEBUG_COPY) + System.out.println("copying pending statement: " + NameUtils.toString(graph, srcStm.stm)); + graph.claim(subjectCopy, srcStm.stm.getPredicate(), srcStm.inverse, objectCopy); + } } private static Resource copy2(final WriteGraph graph, final Resource source, final int level, - BinaryFunction advisor, Map copyMap) + BiFunction advisor, Map copyMap, + Set pendingSourceStatements) throws DatabaseException { if (DEBUG_COPY) System.out.println("[" + level + "] CopyAdvisorUtil.copy(" + NameUtils.getSafeName(graph, source) + ", advisor=" + advisor + ")"); @@ -496,12 +549,18 @@ public class CopyAdvisorUtil { if (DEBUG_COPY) System.out.println("[" + level + "]\t\tcopy whole object"); - Resource clone = copy2(graph, obj, level + 1, advisor, copyMap); + Resource clone = copy2(graph, obj, level + 1, advisor, copyMap, pendingSourceStatements); graph.claim(copy, relation, inverse, clone); } } else { - if (DEBUG_COPY) - System.out.println("[" + level + "]\t\tskipping statement"); + if (graph.isSubrelationOf(relation, L0.IsRelatedTo)) { + if (DEBUG_COPY) + System.out.println("[" + level + "]\t\tmarking statement as pending for post-processing"); + pendingSourceStatements.add(new Statement4(stm, inverse)); + } else { + if (DEBUG_COPY) + System.out.println("[" + level + "]\t\tskipping weak statement"); + } } } } @@ -536,7 +595,7 @@ public class CopyAdvisorUtil { * @throws DatabaseException */ public static Resource copy3(WriteGraph graph, Resource source, Resource model, - BinaryFunction advisor) throws DatabaseException { + BiFunction advisor) throws DatabaseException { String modelURI = graph.getURI(model); return copy3(graph, modelURI, source, 0, advisor, new THashMap()); } @@ -554,13 +613,13 @@ public class CopyAdvisorUtil { * @throws DatabaseException */ public static Resource copy3(WriteGraph graph, Resource source, Resource model, - BinaryFunction advisor, Map copyMap) throws DatabaseException { + BiFunction advisor, Map copyMap) throws DatabaseException { String modelURI = graph.getURI(model); return copy3(graph, modelURI, source, 0, advisor, copyMap); } private static Resource copy3(WriteGraph graph, String modelURI, Resource source, int level, - BinaryFunction advisor, Map copyMap) + BiFunction advisor, Map copyMap) throws DatabaseException { if (DEBUG_COPY) System.out.println("[" + level + "] CopyAdvisorUtil.copy(" + NameUtils.getSafeName(graph, source) + ", advisor=" + advisor + ")"); @@ -698,10 +757,10 @@ public class CopyAdvisorUtil { return copy; } - protected static StatementEvaluation evaluate(ReadGraph graph, Statement stm, BinaryFunction tester) { + protected static StatementEvaluation evaluate(ReadGraph graph, Statement stm, BiFunction tester) { if (tester == null) return StatementEvaluation.USE_DEFAULT; - return tester.call(graph, stm); + return tester.apply(graph, stm); } /** @@ -736,7 +795,7 @@ public class CopyAdvisorUtil { */ public static Resource copy4(WriteGraph graph, Resource source, CopyHandler copyHandler) throws DatabaseException { SimanticsClipboardImpl builder = new SimanticsClipboardImpl(); - copyHandler.copyToClipboard(graph, builder); + copyHandler.copyToClipboard(graph, builder, new NullProgressMonitor()); for(Set object : builder.getContents()) { TransferableGraph1 tg = ClipboardUtils.accept(graph, object, SimanticsKeys.KEY_TRANSFERABLE_GRAPH);