public void SimpleTreeLayoutAlgorithm(
            [NotNull] IBidirectionalGraph <string, Edge <string> > graph,
            int maxCrossCount)
        {
            IDictionary <string, Size> verticesSizes = GetVerticesSizes(graph.Vertices);

            var parameters = new SimpleTreeLayoutParameters
            {
                LayerGap  = 15,
                VertexGap = 20
            };

            foreach (LayoutDirection direction in Enum.GetValues(typeof(LayoutDirection)))
            {
                parameters.Direction = direction;

                foreach (SpanningTreeGeneration treeGen in Enum.GetValues(typeof(SpanningTreeGeneration)))
                {
                    parameters.SpanningTreeGeneration = treeGen;

                    var algorithm = new SimpleTreeLayoutAlgorithm <string, Edge <string>, IBidirectionalGraph <string, Edge <string> > >(
                        graph,
                        verticesSizes,
                        parameters);

                    LayoutResults results = ExecuteLayoutAlgorithm(algorithm, verticesSizes);
                    results.CheckResult(maxCrossCount);
                    CheckTreeLayout(algorithm, verticesSizes);
                }
            }
        }
Beispiel #2
0
        /// <summary>
        /// Performs the actual layout algorithm.
        /// </summary>
        /// <param name="graph">The object containing the graph data</param>
        /// <param name="rootNode">Root node</param>
        protected override void PerformLayout(GraphMapData graph, INode rootNode)
        {
            BidirectionalGraph<string, WeightedEdge<string>> bGraph = GraphSharpUtility.GetBidirectionalGraph(graph);
            IDictionary<string, Vector> nodePositions = GraphSharpUtility.GetNodePositions(graph);
            IDictionary<string, Size> nodeSizes = GraphSharpUtility.GetNodeSizes(graph);
            SimpleTreeLayoutParameters simpleTreeLayoutParameters = new SimpleTreeLayoutParameters();

            SimpleTreeLayoutAlgorithm<string, WeightedEdge<string>, BidirectionalGraph<string, WeightedEdge<string>>> simpleTreeLayoutAlgorithm = new SimpleTreeLayoutAlgorithm<string, WeightedEdge<string>, BidirectionalGraph<string, WeightedEdge<string>>>(bGraph, nodePositions, nodeSizes, simpleTreeLayoutParameters);
            simpleTreeLayoutAlgorithm.Compute();

            GraphSharpUtility.SetNodePositions(graph, simpleTreeLayoutAlgorithm.VertexPositions);
        }
Beispiel #3
0
        private void Relayout(object sender, EventArgs e)
        {
            Task.Run(() =>
            {
                Task.Delay(500).Wait();
                Dispatcher.Invoke(() =>
                {
                    var w = ((UI.VM.MainWindow)DataContext).CurrentWorkspace;

                    var sizes = w.Vertices.ToDictionary(x => x, x => ((UIElement)DrawingArea.ItemContainerGenerator.ContainerFromItem(x))?.DesiredSize ?? new Size(0, 0));
                    GraphSharp.Algorithms.Layout.ILayoutAlgorithm <IGraphNode, ProducibleItem, Workspace> alg;
                    if (w.VertexCount < 3)
                    {
                        alg = new SimpleTreeLayoutAlgorithm <IGraphNode, ProducibleItem, Workspace>(w, new Dictionary <IGraphNode, Point>(), sizes, new SimpleTreeLayoutParameters {
                            VertexGap = 50
                        });
                    }
                    else
                    {
                        alg = new SugiyamaLayoutAlgorithm <IGraphNode, UI.VM.ProducibleItem, Workspace>(w, sizes, new Dictionary <IGraphNode, Point>(), new SugiyamaLayoutParameters {
                            HorizontalGap = 50, VerticalGap = 50
                        }, edge => EdgeTypes.Hierarchical);
                    }

                    //var alg = new EfficientSugiyamaLayoutAlgorithm<IGraphNode, UI.VM.ProducibleItem, Workspace>(w, new EfficientSugiyamaLayoutParameters{VertexDistance = 100,PositionMode = 1}, new Dictionary<IGraphNode, Point>(), sizes);
                    alg.Compute();
                    var offX = 0.0;
                    var offY = 0.0;
                    foreach (var p in alg.VertexPositions)
                    {
                        if (p.Value.X < offX)
                        {
                            offX = p.Value.X;
                        }
                        if (p.Value.Y < offY)
                        {
                            offY = p.Value.Y;
                        }
                    }

                    foreach (var p in alg.VertexPositions)
                    {
                        if (!(p.Key is BaseFlowNode n))
                        {
                            continue;
                        }
                        n.LayoutLeft = p.Value.X - offX;
                        n.LayoutTop  = p.Value.Y - offY;
                    }
                });
            });
        }
Beispiel #4
0
        static SettingsDialog()
        {
            sKKLayoutSettings = new KKLayoutAlgorithm <StateNode, StateEdge>(
                new Digraph <StateNode, StateEdge>(), new Box2F(0, 0, 1, 1));
            sKKLayoutSettings.LengthFactor = 1.25f;

            sBalloonCirclesLayoutSettings = new BalloonCirclesLayoutAlgorithm2 <StateNode, StateEdge>(
                new Digraph <StateNode, StateEdge>(), new Box2F(0, 0, 1, 1));

            sSimpleTreeLayoutSettings = new SimpleTreeLayoutAlgorithm <DGNode, DGEdge>(
                new Digraph <DGNode, DGEdge>(), new Box2F(0, 0, 1, 1));
            sSimpleTreeLayoutSettings.LayerGap = 30;
        }
        static SettingsDialog()
        {
            sKKLayoutSettings = new KKLayoutAlgorithm<StateNode, StateEdge>(
                new Digraph<StateNode, StateEdge>(), new Box2F(0, 0, 1, 1));
            sKKLayoutSettings.LengthFactor = 1.25f;

            sBalloonCirclesLayoutSettings = new BalloonCirclesLayoutAlgorithm2<StateNode, StateEdge>(
                new Digraph<StateNode, StateEdge>(), new Box2F(0, 0, 1, 1));

            sSimpleTreeLayoutSettings = new SimpleTreeLayoutAlgorithm<DGNode, DGEdge>(
                new Digraph<DGNode, DGEdge>(), new Box2F(0, 0, 1, 1));
            sSimpleTreeLayoutSettings.LayerGap = 30;
        }
Beispiel #6
0
        private static void CopyLayoutSettings(
            SimpleTreeLayoutAlgorithm <DGNode, DGEdge> source,
            SimpleTreeLayoutAlgorithm <DGNode, DGEdge> target)
        {
            if (target.State != ComputeState.Running &&
                target.AsyncState != ComputeState.Running)
            {
                target.MaxIterations     = source.MaxIterations;
                target.MovementTolerance = source.MovementTolerance;
            }
            target.SpanningTreeGeneration = source.SpanningTreeGeneration;
            target.RootFindingMethod      = source.RootFindingMethod;

            target.VertexGap          = source.VertexGap;
            target.LayerGap           = source.LayerGap;
            target.Direction          = source.Direction;
            target.AdaptToSizeChanges = source.AdaptToSizeChanges;
            target.AdjustRootCenters  = source.AdjustRootCenters;
            target.SpringMultiplier   = source.SpringMultiplier;
            target.MagneticMultiplier = source.MagneticMultiplier;
            target.MagneticExponent   = source.MagneticExponent;
        }
Beispiel #7
0
        public StateNode(State state, StateMachineScene scene)
            : base(scene)
        {
            if (state == null)
            {
                throw new ArgumentNullException("state");
            }
            this.mState = state;
            this.mScene = scene;

            this.mRad        = sMaxRad;
            this.mRadSquared = sMaxRad * sMaxRad;

            this.bInEditMode = false;

            this.bMinimized = false;

            this.ClipsChildrenToShape = true;

            this.mCluster = new DGNCluster(this);
            this.InitDecisionGraph();

            this.DGLayoutRunning = true;

            this.mLayout = new SimpleTreeLayoutAlgorithm <DGNode, DGEdge>(
                this.mDGraph, this.mCluster);
            this.mLayout.Direction         = LayoutDirection.LeftToRight;
            this.mLayout.LayerGap          = 30;
            this.mLayout.RootFindingMethod = TreeRootFinding.UserDefined;
            if (this.mDGraph.NodeCount > 0)
            {
                this.mLayout.AddRoot(0);
            }
            this.mLayout.ShuffleNodes();

            float rad = this.mRad + 10;

            this.BoundingBox = new RectangleF(-rad, -rad, 2 * rad, 2 * rad);
        }
        public void Constructor()
        {
            var verticesPositions = new Dictionary <string, Point>();
            var verticesSizes     = new Dictionary <string, Size>();
            var graph             = new BidirectionalGraph <string, Edge <string> >();
            var algorithm         = new SimpleTreeLayoutAlgorithm <string, Edge <string>, IBidirectionalGraph <string, Edge <string> > >(graph, verticesSizes);

            AssertAlgorithmProperties(algorithm, graph);

            algorithm = new SimpleTreeLayoutAlgorithm <string, Edge <string>, IBidirectionalGraph <string, Edge <string> > >(graph, verticesSizes);
            algorithm.IterationEnded += (sender, args) => { };
            AssertAlgorithmProperties(algorithm, graph, expectedReportIterationEnd: true);

            algorithm = new SimpleTreeLayoutAlgorithm <string, Edge <string>, IBidirectionalGraph <string, Edge <string> > >(graph, verticesSizes);
            algorithm.ProgressChanged += (sender, args) => { };
            AssertAlgorithmProperties(algorithm, graph, expectedReportProgress: true);

            algorithm = new SimpleTreeLayoutAlgorithm <string, Edge <string>, IBidirectionalGraph <string, Edge <string> > >(graph, verticesSizes);
            algorithm.IterationEnded  += (sender, args) => { };
            algorithm.ProgressChanged += (sender, args) => { };
            AssertAlgorithmProperties(algorithm, graph, expectedReportIterationEnd: true, expectedReportProgress: true);

            algorithm = new SimpleTreeLayoutAlgorithm <string, Edge <string>, IBidirectionalGraph <string, Edge <string> > >(graph, null, verticesSizes);
            AssertAlgorithmProperties(algorithm, graph);

            algorithm = new SimpleTreeLayoutAlgorithm <string, Edge <string>, IBidirectionalGraph <string, Edge <string> > >(graph, verticesPositions, verticesSizes);
            AssertAlgorithmProperties(algorithm, graph, verticesPositions);

            var parameters = new SimpleTreeLayoutParameters();

            algorithm = new SimpleTreeLayoutAlgorithm <string, Edge <string>, IBidirectionalGraph <string, Edge <string> > >(graph, verticesSizes, parameters);
            AssertAlgorithmProperties(algorithm, graph, parameters: parameters);

            algorithm = new SimpleTreeLayoutAlgorithm <string, Edge <string>, IBidirectionalGraph <string, Edge <string> > >(graph, verticesPositions, verticesSizes, parameters);
            AssertAlgorithmProperties(algorithm, graph, verticesPositions, parameters: parameters);
        }
        /// <inheritdoc />
        protected override void InternalCompute()
        {
            // Separate the two sides
            SeparateSides(
                VisitedGraph,
                _root,
                out HashSet <TVertex> side1,
                out HashSet <TVertex> side2);

            // Build the temporary graph for the two sides
            BuildTemporaryGraphs(
                side1,
                side2,
                out BidirectionalGraph <TVertex, Edge <TVertex> > graph1,
                out BidirectionalGraph <TVertex, TEdge> graph2);

            VerticesInfos[_root] = DoubleTreeVertexType.Center;

            ComputeLayoutDirections(out LayoutDirection side1Direction, out LayoutDirection side2Direction);

            // SimpleTree layout on the two side
            var side1LayoutAlgorithm = new SimpleTreeLayoutAlgorithm <TVertex, Edge <TVertex>, BidirectionalGraph <TVertex, Edge <TVertex> > >(
                graph1,
                VerticesPositions,
                _verticesSizes,
                new SimpleTreeLayoutParameters
            {
                LayerGap  = Parameters.LayerGap,
                VertexGap = Parameters.VertexGap,
                Direction = side1Direction,
                SpanningTreeGeneration = SpanningTreeGeneration.BFS
            });

            var side2LayoutAlgorithm = new SimpleTreeLayoutAlgorithm <TVertex, TEdge, BidirectionalGraph <TVertex, TEdge> >(
                graph2,
                VerticesPositions,
                _verticesSizes,
                new SimpleTreeLayoutParameters
            {
                LayerGap  = Parameters.LayerGap,
                VertexGap = Parameters.VertexGap,
                Direction = side2Direction,
                SpanningTreeGeneration = SpanningTreeGeneration.BFS
            });

            side1LayoutAlgorithm.Compute();
            side2LayoutAlgorithm.Compute();

            // Merge the layouts
            Vector side2Translate = side1LayoutAlgorithm.VerticesPositions[_root] - side2LayoutAlgorithm.VerticesPositions[_root];

            foreach (TVertex vertex in side1)
            {
                VerticesPositions[vertex] = side1LayoutAlgorithm.VerticesPositions[vertex];
            }

            foreach (TVertex vertex in side2)
            {
                VerticesPositions[vertex] = side2LayoutAlgorithm.VerticesPositions[vertex] + side2Translate;
            }

            NormalizePositions();
        }
        protected override void InternalCompute()
        {
            //
            // Separate the two sides
            //
            HashSet <TVertex> side1, side2;

            SeparateSides(VisitedGraph, root, out side1, out side2);

            #region Build the temporary graph for the two sides

            //
            // The IN side
            //
            //on the IN side we should reverse the edges
            var graph1 = new BidirectionalGraph <TVertex, Edge <TVertex> >();
            graph1.AddVertexRange(side1);
            foreach (var v in side1)
            {
                vertexInfos[v] = DoubleTreeVertexType.Backward;
                foreach (var e in VisitedGraph.InEdges(v))
                {
                    if (!side1.Contains(e.Source) || e.Source.Equals(e.Target))
                    {
                        continue;
                    }

                    //reverse the edge
                    graph1.AddEdge(new Edge <TVertex>(e.Target, e.Source));
                }
            }

            //
            // The OUT side
            //
            var graph2 = new BidirectionalGraph <TVertex, TEdge>();
            graph2.AddVertexRange(side2);
            foreach (var v in side2)
            {
                vertexInfos[v] = DoubleTreeVertexType.Forward;
                foreach (var e in VisitedGraph.OutEdges(v))
                {
                    if (!side2.Contains(e.Target) || e.Source.Equals(e.Target))
                    {
                        continue;
                    }

                    //simply add the edge
                    graph2.AddEdge(e);
                }
            }

            vertexInfos[root] = DoubleTreeVertexType.Center;
            #endregion

            LayoutDirection side2Direction = Parameters.Direction;
            LayoutDirection side1Direction = Parameters.Direction;
            switch (side2Direction)
            {
            case LayoutDirection.BottomToTop:
                side1Direction = LayoutDirection.TopToBottom;
                break;

            case LayoutDirection.LeftToRight:
                side1Direction = LayoutDirection.RightToLeft;
                break;

            case LayoutDirection.RightToLeft:
                side1Direction = LayoutDirection.LeftToRight;
                break;

            case LayoutDirection.TopToBottom:
                side1Direction = LayoutDirection.BottomToTop;
                break;
            }

            //
            // SimpleTree layout on the two side
            //
            var side1LayoutAlg = new SimpleTreeLayoutAlgorithm <TVertex, Edge <TVertex>, BidirectionalGraph <TVertex, Edge <TVertex> > >(
                graph1, VertexPositions, vertexSizes,
                new SimpleTreeLayoutParameters
            {
                LayerGap  = Parameters.LayerGap,
                VertexGap = Parameters.VertexGap,
                Direction = side1Direction,
                SpanningTreeGeneration = SpanningTreeGeneration.BFS
            });
            var side2LayoutAlg = new SimpleTreeLayoutAlgorithm <TVertex, TEdge, BidirectionalGraph <TVertex, TEdge> >(
                graph2, VertexPositions, vertexSizes,
                new SimpleTreeLayoutParameters
            {
                LayerGap  = Parameters.LayerGap,
                VertexGap = Parameters.VertexGap,
                Direction = side2Direction,
                SpanningTreeGeneration = SpanningTreeGeneration.BFS
            });

            side1LayoutAlg.Compute();
            side2LayoutAlg.Compute();

            //
            // Merge the layouts
            //
            var side2Translate = side1LayoutAlg.VertexPositions[root] - side2LayoutAlg.VertexPositions[root];
            foreach (var v in side1)
            {
                VertexPositions[v] = side1LayoutAlg.VertexPositions[v];
            }

            foreach (var v in side2)
            {
                VertexPositions[v] = side2LayoutAlg.VertexPositions[v] + side2Translate;
            }
            NormalizePositions();
        }
        private static void CopyLayoutSettings(
            SimpleTreeLayoutAlgorithm<DGNode, DGEdge> source,
            SimpleTreeLayoutAlgorithm<DGNode, DGEdge> target)
        {
            if (target.State != ComputeState.Running &&
                target.AsyncState != ComputeState.Running)
            {
                target.MaxIterations = source.MaxIterations;
                target.MovementTolerance = source.MovementTolerance;
            }
            target.SpanningTreeGeneration = source.SpanningTreeGeneration;
            target.RootFindingMethod = source.RootFindingMethod;

            target.VertexGap = source.VertexGap;
            target.LayerGap = source.LayerGap;
            target.Direction = source.Direction;
            target.AdaptToSizeChanges = source.AdaptToSizeChanges;
            target.AdjustRootCenters = source.AdjustRootCenters;
            target.SpringMultiplier = source.SpringMultiplier;
            target.MagneticMultiplier = source.MagneticMultiplier;
            target.MagneticExponent = source.MagneticExponent;
        }
        public void StandardFactory()
        {
            var positions     = new Dictionary <TestVertex, Point>();
            var sizes         = new Dictionary <TestVertex, Size>();
            var borders       = new Dictionary <TestVertex, Thickness>();
            var layoutTypes   = new Dictionary <TestVertex, CompoundVertexInnerLayoutType>();
            var graph         = new BidirectionalGraph <TestVertex, Edge <TestVertex> >();
            var simpleContext = new LayoutContext <TestVertex, Edge <TestVertex>, BidirectionalGraph <TestVertex, Edge <TestVertex> > >(
                graph,
                positions,
                sizes,
                LayoutMode.Simple);
            var compoundContext1 = new LayoutContext <TestVertex, Edge <TestVertex>, BidirectionalGraph <TestVertex, Edge <TestVertex> > >(
                graph,
                positions,
                sizes,
                LayoutMode.Compound);
            var compoundContext2 = new CompoundLayoutContext <TestVertex, Edge <TestVertex>, BidirectionalGraph <TestVertex, Edge <TestVertex> > >(
                graph,
                positions,
                sizes,
                LayoutMode.Compound,
                borders,
                layoutTypes);
            var nullGraphContext = new LayoutContext <TestVertex, Edge <TestVertex>, BidirectionalGraph <TestVertex, Edge <TestVertex> > >(
                null,
                positions,
                sizes,
                LayoutMode.Simple);

            var factory = new StandardLayoutAlgorithmFactory <TestVertex, Edge <TestVertex>, BidirectionalGraph <TestVertex, Edge <TestVertex> > >();

            CollectionAssert.AreEqual(
                new[]
            {
                "Circular", "Tree", "FR", "BoundedFR", "KK",
                "ISOM", "LinLog", "Sugiyama", "CompoundFDP",
                "Random"
            },
                factory.AlgorithmTypes);


            Assert.IsNull(
                factory.CreateAlgorithm(
                    string.Empty,
                    simpleContext,
                    new CircularLayoutParameters()));

            Assert.IsNull(
                factory.CreateAlgorithm(
                    "NotExist",
                    simpleContext,
                    new CircularLayoutParameters()));

            Assert.IsNull(
                factory.CreateAlgorithm(
                    "Circular",
                    nullGraphContext,
                    new CircularLayoutParameters()));

            Assert.IsInstanceOf <CircularLayoutAlgorithm <TestVertex, Edge <TestVertex>, BidirectionalGraph <TestVertex, Edge <TestVertex> > > >(
                factory.CreateAlgorithm(
                    "Circular",
                    simpleContext,
                    new CircularLayoutParameters()));

            Assert.IsInstanceOf <SimpleTreeLayoutAlgorithm <TestVertex, Edge <TestVertex>, BidirectionalGraph <TestVertex, Edge <TestVertex> > > >(
                factory.CreateAlgorithm(
                    "Tree",
                    simpleContext,
                    new SimpleTreeLayoutParameters()));

            Assert.IsInstanceOf <FRLayoutAlgorithm <TestVertex, Edge <TestVertex>, BidirectionalGraph <TestVertex, Edge <TestVertex> > > >(
                factory.CreateAlgorithm(
                    "FR",
                    simpleContext,
                    new FreeFRLayoutParameters()));

            Assert.IsInstanceOf <FRLayoutAlgorithm <TestVertex, Edge <TestVertex>, BidirectionalGraph <TestVertex, Edge <TestVertex> > > >(
                factory.CreateAlgorithm(
                    "BoundedFR",
                    simpleContext,
                    new BoundedFRLayoutParameters()));

            Assert.IsInstanceOf <KKLayoutAlgorithm <TestVertex, Edge <TestVertex>, BidirectionalGraph <TestVertex, Edge <TestVertex> > > >(
                factory.CreateAlgorithm(
                    "KK",
                    simpleContext,
                    new KKLayoutParameters()));

            Assert.IsInstanceOf <ISOMLayoutAlgorithm <TestVertex, Edge <TestVertex>, BidirectionalGraph <TestVertex, Edge <TestVertex> > > >(
                factory.CreateAlgorithm(
                    "ISOM",
                    simpleContext,
                    new ISOMLayoutParameters()));

            Assert.IsInstanceOf <LinLogLayoutAlgorithm <TestVertex, Edge <TestVertex>, BidirectionalGraph <TestVertex, Edge <TestVertex> > > >(
                factory.CreateAlgorithm(
                    "LinLog",
                    simpleContext,
                    new LinLogLayoutParameters()));

            Assert.IsInstanceOf <SugiyamaLayoutAlgorithm <TestVertex, Edge <TestVertex>, BidirectionalGraph <TestVertex, Edge <TestVertex> > > >(
                factory.CreateAlgorithm(
                    "Sugiyama",
                    simpleContext,
                    new SugiyamaLayoutParameters()));

            Assert.IsInstanceOf <CompoundFDPLayoutAlgorithm <TestVertex, Edge <TestVertex>, BidirectionalGraph <TestVertex, Edge <TestVertex> > > >(
                factory.CreateAlgorithm(
                    "CompoundFDP",
                    simpleContext,
                    new CompoundFDPLayoutParameters()));

            Assert.IsInstanceOf <RandomLayoutAlgorithm <TestVertex, Edge <TestVertex>, BidirectionalGraph <TestVertex, Edge <TestVertex> > > >(
                factory.CreateAlgorithm(
                    "Random",
                    simpleContext,
                    new RandomLayoutParameters()));

            Assert.IsNull(
                factory.CreateAlgorithm(
                    "CompoundFDP",
                    compoundContext1,
                    new CompoundFDPLayoutParameters()));

            Assert.IsNull(
                factory.CreateAlgorithm(
                    "Circular",
                    compoundContext2,
                    new CompoundFDPLayoutParameters()));

            Assert.IsInstanceOf <CompoundFDPLayoutAlgorithm <TestVertex, Edge <TestVertex>, BidirectionalGraph <TestVertex, Edge <TestVertex> > > >(
                factory.CreateAlgorithm(
                    "CompoundFDP",
                    compoundContext2,
                    new CompoundFDPLayoutParameters()));


            var testParameters     = new TestLayoutParameters();
            var circularParameters = new CircularLayoutParameters();
            ILayoutParameters createdParameters = factory.CreateParameters(string.Empty, circularParameters);

            Assert.IsNull(createdParameters);

            createdParameters = factory.CreateParameters("NotExist", circularParameters);
            Assert.IsNull(createdParameters);

            createdParameters = factory.CreateParameters("Circular", null);
            Assert.IsInstanceOf <CircularLayoutParameters>(createdParameters);
            Assert.AreNotSame(circularParameters, createdParameters);

            createdParameters = factory.CreateParameters("Circular", testParameters);
            Assert.IsInstanceOf <CircularLayoutParameters>(createdParameters);
            Assert.AreNotSame(testParameters, createdParameters);

            createdParameters = factory.CreateParameters("Circular", circularParameters);
            Assert.IsInstanceOf <CircularLayoutParameters>(createdParameters);
            Assert.AreNotSame(circularParameters, createdParameters);

            var treeParameters = new SimpleTreeLayoutParameters();

            createdParameters = factory.CreateParameters("Tree", null);
            Assert.IsInstanceOf <SimpleTreeLayoutParameters>(createdParameters);
            Assert.AreNotSame(treeParameters, createdParameters);

            createdParameters = factory.CreateParameters("Tree", testParameters);
            Assert.IsInstanceOf <SimpleTreeLayoutParameters>(createdParameters);
            Assert.AreNotSame(testParameters, createdParameters);

            createdParameters = factory.CreateParameters("Tree", treeParameters);
            Assert.IsInstanceOf <SimpleTreeLayoutParameters>(createdParameters);
            Assert.AreNotSame(treeParameters, createdParameters);

            var frParameters = new FreeFRLayoutParameters();

            createdParameters = factory.CreateParameters("FR", null);
            Assert.IsInstanceOf <FreeFRLayoutParameters>(createdParameters);
            Assert.AreNotSame(frParameters, createdParameters);

            createdParameters = factory.CreateParameters("FR", testParameters);
            Assert.IsInstanceOf <FreeFRLayoutParameters>(createdParameters);
            Assert.AreNotSame(treeParameters, createdParameters);

            createdParameters = factory.CreateParameters("FR", frParameters);
            Assert.IsInstanceOf <FreeFRLayoutParameters>(createdParameters);
            Assert.AreNotSame(frParameters, createdParameters);

            var boundedFrParameters = new BoundedFRLayoutParameters();

            createdParameters = factory.CreateParameters("BoundedFR", null);
            Assert.IsInstanceOf <BoundedFRLayoutParameters>(createdParameters);
            Assert.AreNotSame(boundedFrParameters, createdParameters);

            createdParameters = factory.CreateParameters("BoundedFR", testParameters);
            Assert.IsInstanceOf <BoundedFRLayoutParameters>(createdParameters);
            Assert.AreNotSame(treeParameters, createdParameters);

            createdParameters = factory.CreateParameters("BoundedFR", boundedFrParameters);
            Assert.IsInstanceOf <BoundedFRLayoutParameters>(createdParameters);
            Assert.AreNotSame(boundedFrParameters, createdParameters);

            var kkParameters = new KKLayoutParameters();

            createdParameters = factory.CreateParameters("KK", null);
            Assert.IsInstanceOf <KKLayoutParameters>(createdParameters);
            Assert.AreNotSame(kkParameters, createdParameters);

            createdParameters = factory.CreateParameters("KK", testParameters);
            Assert.IsInstanceOf <KKLayoutParameters>(createdParameters);
            Assert.AreNotSame(treeParameters, createdParameters);

            createdParameters = factory.CreateParameters("KK", kkParameters);
            Assert.IsInstanceOf <KKLayoutParameters>(createdParameters);
            Assert.AreNotSame(kkParameters, createdParameters);

            var isomParameters = new ISOMLayoutParameters();

            createdParameters = factory.CreateParameters("ISOM", null);
            Assert.IsInstanceOf <ISOMLayoutParameters>(createdParameters);
            Assert.AreNotSame(isomParameters, createdParameters);

            createdParameters = factory.CreateParameters("ISOM", testParameters);
            Assert.IsInstanceOf <ISOMLayoutParameters>(createdParameters);
            Assert.AreNotSame(treeParameters, createdParameters);

            createdParameters = factory.CreateParameters("ISOM", isomParameters);
            Assert.IsInstanceOf <ISOMLayoutParameters>(createdParameters);
            Assert.AreNotSame(isomParameters, createdParameters);

            var linLogParameters = new LinLogLayoutParameters();

            createdParameters = factory.CreateParameters("LinLog", null);
            Assert.IsInstanceOf <LinLogLayoutParameters>(createdParameters);
            Assert.AreNotSame(linLogParameters, createdParameters);

            createdParameters = factory.CreateParameters("LinLog", testParameters);
            Assert.IsInstanceOf <LinLogLayoutParameters>(createdParameters);
            Assert.AreNotSame(treeParameters, createdParameters);

            createdParameters = factory.CreateParameters("LinLog", linLogParameters);
            Assert.IsInstanceOf <LinLogLayoutParameters>(createdParameters);
            Assert.AreNotSame(linLogParameters, createdParameters);

            var sugiyamaParameters = new SugiyamaLayoutParameters();

            createdParameters = factory.CreateParameters("Sugiyama", null);
            Assert.IsInstanceOf <SugiyamaLayoutParameters>(createdParameters);
            Assert.AreNotSame(sugiyamaParameters, createdParameters);

            createdParameters = factory.CreateParameters("Sugiyama", testParameters);
            Assert.IsInstanceOf <SugiyamaLayoutParameters>(createdParameters);
            Assert.AreNotSame(treeParameters, createdParameters);

            createdParameters = factory.CreateParameters("Sugiyama", sugiyamaParameters);
            Assert.IsInstanceOf <SugiyamaLayoutParameters>(createdParameters);
            Assert.AreNotSame(sugiyamaParameters, createdParameters);

            var compoundFDPParameters = new CompoundFDPLayoutParameters();

            createdParameters = factory.CreateParameters("CompoundFDP", null);
            Assert.IsInstanceOf <CompoundFDPLayoutParameters>(createdParameters);
            Assert.AreNotSame(compoundFDPParameters, createdParameters);

            createdParameters = factory.CreateParameters("CompoundFDP", testParameters);
            Assert.IsInstanceOf <CompoundFDPLayoutParameters>(createdParameters);
            Assert.AreNotSame(treeParameters, createdParameters);

            createdParameters = factory.CreateParameters("CompoundFDP", compoundFDPParameters);
            Assert.IsInstanceOf <CompoundFDPLayoutParameters>(createdParameters);
            Assert.AreNotSame(compoundFDPParameters, createdParameters);

            var randomParameters = new RandomLayoutParameters();

            createdParameters = factory.CreateParameters("Random", null);
            Assert.IsInstanceOf <RandomLayoutParameters>(createdParameters);
            Assert.AreNotSame(randomParameters, createdParameters);

            createdParameters = factory.CreateParameters("Random", testParameters);
            Assert.IsInstanceOf <RandomLayoutParameters>(createdParameters);
            Assert.AreNotSame(treeParameters, createdParameters);

            createdParameters = factory.CreateParameters("Random", randomParameters);
            Assert.IsInstanceOf <RandomLayoutParameters>(createdParameters);
            Assert.AreNotSame(randomParameters, createdParameters);


            Assert.IsFalse(factory.IsValidAlgorithm(null));
            Assert.IsFalse(factory.IsValidAlgorithm(string.Empty));
            Assert.IsTrue(factory.IsValidAlgorithm("Circular"));
            Assert.IsFalse(factory.IsValidAlgorithm("circular"));
            Assert.IsTrue(factory.IsValidAlgorithm("Tree"));
            Assert.IsTrue(factory.IsValidAlgorithm("FR"));
            Assert.IsTrue(factory.IsValidAlgorithm("BoundedFR"));
            Assert.IsTrue(factory.IsValidAlgorithm("KK"));
            Assert.IsTrue(factory.IsValidAlgorithm("ISOM"));
            Assert.IsTrue(factory.IsValidAlgorithm("LinLog"));
            Assert.IsTrue(factory.IsValidAlgorithm("Sugiyama"));
            Assert.IsTrue(factory.IsValidAlgorithm("CompoundFDP"));
            Assert.IsTrue(factory.IsValidAlgorithm("Random"));


            var algorithm1 = new TestLayoutAlgorithm();

            Assert.IsEmpty(factory.GetAlgorithmType(algorithm1));

            var algorithm2 = new CircularLayoutAlgorithm <TestVertex, Edge <TestVertex>, BidirectionalGraph <TestVertex, Edge <TestVertex> > >(graph, positions, sizes, circularParameters);

            Assert.AreEqual("Circular", factory.GetAlgorithmType(algorithm2));

            var algorithm3 = new SimpleTreeLayoutAlgorithm <TestVertex, Edge <TestVertex>, BidirectionalGraph <TestVertex, Edge <TestVertex> > >(graph, positions, sizes, treeParameters);

            Assert.AreEqual("Tree", factory.GetAlgorithmType(algorithm3));

            var algorithm4 = new FRLayoutAlgorithm <TestVertex, Edge <TestVertex>, BidirectionalGraph <TestVertex, Edge <TestVertex> > >(graph, positions, frParameters);

            Assert.AreEqual("FR", factory.GetAlgorithmType(algorithm4));

            var algorithm5 = new FRLayoutAlgorithm <TestVertex, Edge <TestVertex>, BidirectionalGraph <TestVertex, Edge <TestVertex> > >(graph, positions, boundedFrParameters);

            Assert.AreEqual("BoundedFR", factory.GetAlgorithmType(algorithm5));

            var algorithm6 = new KKLayoutAlgorithm <TestVertex, Edge <TestVertex>, BidirectionalGraph <TestVertex, Edge <TestVertex> > >(graph, positions, kkParameters);

            Assert.AreEqual("KK", factory.GetAlgorithmType(algorithm6));

            var algorithm7 = new ISOMLayoutAlgorithm <TestVertex, Edge <TestVertex>, BidirectionalGraph <TestVertex, Edge <TestVertex> > >(graph, positions, isomParameters);

            Assert.AreEqual("ISOM", factory.GetAlgorithmType(algorithm7));

            var algorithm8 = new LinLogLayoutAlgorithm <TestVertex, Edge <TestVertex>, BidirectionalGraph <TestVertex, Edge <TestVertex> > >(graph);

            Assert.AreEqual("LinLog", factory.GetAlgorithmType(algorithm8));

            var algorithm9 = new SugiyamaLayoutAlgorithm <TestVertex, Edge <TestVertex>, BidirectionalGraph <TestVertex, Edge <TestVertex> > >(graph, positions, sizes, sugiyamaParameters);

            Assert.AreEqual("Sugiyama", factory.GetAlgorithmType(algorithm9));

            var algorithm10 = new CompoundFDPLayoutAlgorithm <TestVertex, Edge <TestVertex>, BidirectionalGraph <TestVertex, Edge <TestVertex> > >(graph, sizes, borders, layoutTypes);

            Assert.AreEqual("CompoundFDP", factory.GetAlgorithmType(algorithm10));

            var algorithm11 = new RandomLayoutAlgorithm <TestVertex, Edge <TestVertex>, BidirectionalGraph <TestVertex, Edge <TestVertex> > >(graph, sizes, null, randomParameters);

            Assert.AreEqual("Random", factory.GetAlgorithmType(algorithm11));


            Assert.IsFalse(factory.NeedEdgeRouting(string.Empty));
            Assert.IsTrue(factory.NeedEdgeRouting("Circular"));
            Assert.IsTrue(factory.NeedEdgeRouting("Tree"));
            Assert.IsTrue(factory.NeedEdgeRouting("FR"));
            Assert.IsTrue(factory.NeedEdgeRouting("BoundedFR"));
            Assert.IsTrue(factory.NeedEdgeRouting("KK"));
            Assert.IsTrue(factory.NeedEdgeRouting("ISOM"));
            Assert.IsTrue(factory.NeedEdgeRouting("LinLog"));
            Assert.IsFalse(factory.NeedEdgeRouting("Sugiyama"));
            Assert.IsTrue(factory.NeedEdgeRouting("CompoundFDP"));
            Assert.IsTrue(factory.NeedEdgeRouting("Random"));


            Assert.IsFalse(factory.NeedOverlapRemoval(string.Empty));
            Assert.IsFalse(factory.NeedOverlapRemoval("Circular"));
            Assert.IsFalse(factory.NeedOverlapRemoval("Tree"));
            Assert.IsTrue(factory.NeedOverlapRemoval("FR"));
            Assert.IsTrue(factory.NeedOverlapRemoval("BoundedFR"));
            Assert.IsTrue(factory.NeedOverlapRemoval("KK"));
            Assert.IsTrue(factory.NeedOverlapRemoval("ISOM"));
            Assert.IsTrue(factory.NeedOverlapRemoval("LinLog"));
            Assert.IsFalse(factory.NeedOverlapRemoval("Sugiyama"));
            Assert.IsFalse(factory.NeedOverlapRemoval("CompoundFDP"));
            Assert.IsTrue(factory.NeedOverlapRemoval("Random"));
        }
Beispiel #13
0
        /// <summary>
        /// Performs the actual layout algorithm.
        /// </summary>
        /// <param name="graph">The object containing the graph data</param>
        /// <param name="rootNode">Root node</param>
        protected override void PerformLayout(GraphMapData graph, INode rootNode)
        {
            BidirectionalGraph <string, WeightedEdge <string> > bGraph = GraphSharpUtility.GetBidirectionalGraph(graph);
            IDictionary <string, Vector> nodePositions = GraphSharpUtility.GetNodePositions(graph);
            IDictionary <string, Size>   nodeSizes     = GraphSharpUtility.GetNodeSizes(graph);
            SimpleTreeLayoutParameters   simpleTreeLayoutParameters = new SimpleTreeLayoutParameters();

            SimpleTreeLayoutAlgorithm <string, WeightedEdge <string>, BidirectionalGraph <string, WeightedEdge <string> > > simpleTreeLayoutAlgorithm = new SimpleTreeLayoutAlgorithm <string, WeightedEdge <string>, BidirectionalGraph <string, WeightedEdge <string> > >(bGraph, nodePositions, nodeSizes, simpleTreeLayoutParameters);

            simpleTreeLayoutAlgorithm.Compute();

            GraphSharpUtility.SetNodePositions(graph, simpleTreeLayoutAlgorithm.VertexPositions);
        }
        private static void CheckTreeLayout <TVertex, TEdge>(
            [NotNull] SimpleTreeLayoutAlgorithm <TVertex, TEdge, IBidirectionalGraph <TVertex, TEdge> > algorithm,
            [NotNull] IDictionary <TVertex, Size> verticesSizes)
            where TVertex : class
            where TEdge : IEdge <TVertex>
        {
            var slices = new Dictionary <double, HashSet <double> >();

            TVertex[] vertices = algorithm.VisitedGraph.Vertices.ToArray();
            for (int i = 0; i < vertices.Length - 1; ++i)
            {
                TVertex vertexI = vertices[i];
                Point   posI    = algorithm.VerticesPositions[vertexI];
                for (int j = i + 1; j < vertices.Length; ++j)
                {
                    TVertex vertexJ = vertices[j];
                    Point   posJ    = algorithm.VerticesPositions[vertexJ];
                    if (algorithm.Parameters.Direction.IsHorizontal())
                    {
                        CheckSpacingAndAddSlice(posI.Y, verticesSizes[vertexI].Height / 2);
                        CheckSpacingAndAddSlice(posJ.Y, verticesSizes[vertexJ].Height / 2);

                        CheckSpacingAndAddLayerToSlice(posI.Y, posI.X, verticesSizes[vertexI].Width / 2);
                        CheckSpacingAndAddLayerToSlice(posJ.Y, posJ.X, verticesSizes[vertexJ].Width / 2);
                    }
                    else if (algorithm.Parameters.Direction.IsVertical())
                    {
                        CheckSpacingAndAddSlice(posI.X, verticesSizes[vertexI].Width / 2);
                        CheckSpacingAndAddSlice(posJ.X, verticesSizes[vertexJ].Width / 2);

                        CheckSpacingAndAddLayerToSlice(posI.X, posI.Y, verticesSizes[vertexI].Height / 2);
                        CheckSpacingAndAddLayerToSlice(posJ.X, posJ.Y, verticesSizes[vertexJ].Height / 2);
                    }
                    else
                    {
                        throw new NotSupportedException("Not supported layout direction.");
                    }
                }
            }

            #region Local functions

            // ReSharper disable ParameterOnlyUsedForPreconditionCheck.Local
            void CheckSpacingAndAddSlice(double slicePos, double size)
            {
                if (!slices.ContainsKey(slicePos))
                {
                    Assert.IsTrue(slices.All(pair => Math.Abs(slicePos - pair.Key) + size >= algorithm.Parameters.VertexGap));
                    slices.Add(slicePos, new HashSet <double>());
                }
            }

            void CheckSpacingAndAddLayerToSlice(double slicePos, double layerPos, double size)
            {
                Assert.IsTrue(slices.TryGetValue(slicePos, out HashSet <double> layerPositions));
                Assert.IsTrue(layerPositions.All(lPos => Math.Abs(layerPos - lPos) + size >= algorithm.Parameters.LayerGap));
            }

            // ReSharper restore ParameterOnlyUsedForPreconditionCheck.Local

            #endregion
        }