/// <summary> /// Writes the graph to a file /// </summary> public void Write() { CultureInfo currentCulture = Thread.CurrentThread.CurrentCulture; Thread.CurrentThread.CurrentCulture = CultureInfo.InvariantCulture; var matrix = new PlaneTransformation(1, 0, 0, 0, -1, 0); try { graph.GeometryGraph.Transform(matrix); Open(); WriteGraphAttr(graph.Attr); WriteLabel(graph.Label); WriteEdges(); WriteNodes(); #if DEBUG && TEST_MSAGL WriteDebugCurves(); #endif Close(); } finally { //restore the culture graph.GeometryGraph.Transform(matrix); Thread.CurrentThread.CurrentCulture = currentCulture; } }
static void PostRunTransform(GeometryGraph geometryGraph, PlaneTransformation transformation) { bool transform = !transformation.IsIdentity; if (transform) { foreach (Node n in geometryGraph.Nodes) { n.Transform(transformation); } //restore labels widths and heights foreach (Edge e in geometryGraph.Edges) { if (e.Label != null) { e.Label.Width = e.OriginalLabelWidth; e.Label.Height = e.OriginalLabelHeight; } } TransformCurves(geometryGraph, transformation); } geometryGraph.UpdateBoundingBox(); }
/// <summary> /// returns the transformed polyline /// </summary> /// <param name="transformation"></param> /// <returns></returns> public ICurve Transform(PlaneTransformation transformation) { if (transformation == null) { return(this); } var poly = new Polyline { Closed = Closed }; foreach (var p in this) { poly.AddPoint(transformation * p); } return(poly); }
public static void SetGraphTransform(GeometryGraph geometryGraph, System.Drawing.Rectangle rectangle) { //instead of setting transormation for graphics we are going to transform the geometry graph, just to test that GeometryGraph.Transform() works RectangleF clientRectangle = rectangle; var gr = geometryGraph.BoundingBox; if (clientRectangle.Height > 1 && clientRectangle.Width > 1) { var scale = Math.Min(clientRectangle.Width * 0.9 / gr.Width, clientRectangle.Height * 0.9 / gr.Height); var g0 = (gr.Left + gr.Right) / 2; var g1 = (gr.Top + gr.Bottom) / 2; var c0 = (clientRectangle.Left + clientRectangle.Right) / 2; var c1 = (clientRectangle.Top + clientRectangle.Bottom) / 2; var dx = c0 - scale * g0; var dy = c1 - scale * g1; var planeTransformation=new PlaneTransformation(scale,0,dx, 0, scale, dy); geometryGraph.Transform(planeTransformation); } }
internal static void PreRunTransform(GeometryGraph geomGraph, PlaneTransformation matrix) { if (matrix.IsIdentity) return; var matrixInverse = matrix.Inverse; foreach (Node n in geomGraph.Nodes) n.Transform(matrixInverse); //calculate new label widths and heights foreach (Edge e in geomGraph.Edges) { if (e.Label != null) { e.OriginalLabelWidth = e.Label.Width; e.OriginalLabelHeight = e.Label.Height; var r = new Rectangle(matrixInverse*new Point(0, 0), matrixInverse*new Point(e.Label.Width, e.Label.Height)); e.Label.Width = r.Width; e.Label.Height = r.Height; } } geomGraph.UpdateBoundingBox(); }
#pragma warning disable 1591 public void ScaleNodeAroundCenter(IViewerNode viewerNode, double scale) { #pragma warning restore 1591 var nodePosition = viewerNode.Node.BoundingBox.Center; var scaleMatrix = new PlaneTransformation(scale, 0, 0, 0, scale, 0); var translateToOrigin = new PlaneTransformation(1, 0, -nodePosition.X, 0, 1, -nodePosition.Y); var translateToNode = new PlaneTransformation(1, 0, nodePosition.X, 0, 1, nodePosition.Y); var matrix = translateToNode*scaleMatrix*translateToOrigin; viewerNode.Node.GeometryNode.BoundaryCurve=viewerNode.Node.GeometryNode.BoundaryCurve.Transform(matrix); viewer.Invalidate(viewerNode); foreach (var edge in viewerNode.OutEdges.Concat(viewerNode.InEdges).Concat(viewerNode.SelfEdges)) RecoverEdge(edge); }
/// <summary> /// Check whether graph layers in a vertical order /// </summary> /// <returns>True if layer is based on node Y coordinate</returns> private static bool IsVerticallyLayered(PlaneTransformation transformation) { //just check LR and RL cases first, other than that, assume to be TD or DT PlaneTransformation leftRight = PlaneTransformation.Rotation(Math.PI / 2); bool horizontial = true; for (int i = 0; i < 2; i++) { for (int j = 0; j < 3; j++) { if (Math.Abs(transformation.Elements[i][j] - leftRight.Elements[i][j]) > Tolerance) { horizontial = false; break; } } if (!horizontial) { break; } } if (horizontial) { return false; } PlaneTransformation rightLeft = PlaneTransformation.Rotation(-Math.PI / 2); horizontial = true; for (int i = 0; i < 2; i++) { for (int j = 0; j < 3; j++) { if (Math.Abs(transformation.Elements[i][j] - rightLeft.Elements[i][j]) > Tolerance) { horizontial = false; break; } } if (!horizontial) { break; } } return !horizontial; }
void WriteTransformation(PlaneTransformation transformation) { WriteStartElement(GeometryToken.Transform); XmlWriter.WriteComment("the order of elements is [0,0],[0,1],[0,2],[1,0],[1,1],[1,2]"); for (int i = 0; i < 2; i++) for (int j = 0; j < 3; j++) WriteTransformationElement(transformation[i, j]); WriteEndElement(); }
/// <summary> /// matrix matrix multiplication /// </summary> /// <param name="a"></param> /// <param name="b"></param> /// <returns></returns> static public PlaneTransformation Multiply(PlaneTransformation a, PlaneTransformation b) { if (a != null && b != null) return new PlaneTransformation( a[0, 0] * b[0, 0] + a[0, 1] * b[1, 0], a[0, 0] * b[0, 1] + a[0, 1] * b[1, 1], a[0, 0] * b[0, 2] + a[0, 1] * b[1, 2] + a[0, 2], a[1, 0] * b[0, 0] + a[1, 1] * b[1, 0], a[1, 0] * b[0, 1] + a[1, 1] * b[1, 1], a[1, 0] * b[0, 2] + a[1, 1] * b[1, 2] + a[1, 2]); return null; }
/// <summary> /// Point by matrix multiplication /// </summary> /// <param name="transformation"></param> /// <param name="point"></param> /// <returns></returns> static public Point Multiply(PlaneTransformation transformation, Point point) { if (transformation != null) return new Point(transformation[0, 0] * point.X + transformation[0, 1] * point.Y + transformation[0, 2], transformation[1, 0] * point.X + transformation[1, 1] * point.Y + transformation[1, 2]); return new Point(); }
/// <summary> /// Divid matrix by a matrix /// </summary> /// <param name="transformation0"></param> /// <param name="transformation1"></param> /// <returns></returns> static public PlaneTransformation Divide(PlaneTransformation transformation0, PlaneTransformation transformation1) { return transformation0 / transformation1; }
/// <summary> /// Return the transformed curve /// </summary> /// <param name="transformation"></param> /// <returns>the transformed curve</returns> public ICurve Transform(PlaneTransformation transformation) { return(new LineSegment(transformation * a, transformation * b)); }
ICurve ReadEllepticalArc(CurveStream curveStream, ref Point currentPoint) { /* var rx = "A"+DoubleToString(ellipse.AxisA.Length); var ry = DoubleToString(ellipse.AxisB.Length); var xAxisRotation = DoubleToString(180*Point.Angle(new Point(1, 0), ellipse.AxisA)/Math.PI); var largeArcFlag = Math.Abs(ellipse.ParEnd - ellipse.ParStart) >= Math.PI ? "1" : "0"; var sweepFlag = ellipse.ParEnd > ellipse.ParStart ? "1" : "0"; //it happens because of the y-axis orientation down in SVG var endPoint=PointToString(ellipse.End); return string.Join(" ", new[] {rx, ry, xAxisRotation, largeArcFlag, sweepFlag, endPoint}); var endPoint = GetCurveDataPoint(curveStream); */ var rx = GetNextDoubleFromCurveData(curveStream); var ry = GetNextDoubleFromCurveData(curveStream); var xAxisRotation = GetNextDoubleFromCurveData(curveStream)/180*Math.PI; var largeArcFlag = (int) GetNextDoubleFromCurveData(curveStream); var sweepFlag = (int) GetNextDoubleFromCurveData(curveStream); var endPoint = GetNextPointFromCurveData(curveStream); //figure out the transform to the circle //then solve this problem on the circle if (ApproximateComparer.Close(rx, 0) || ApproximateComparer.Close(ry, 0)) Error("ellipseArc radius is too small"); var yScale = rx/ry; var rotationMatrix = PlaneTransformation.Rotation(-xAxisRotation); var scaleMatrix = new PlaneTransformation(1, 0, 0, 0, yScale, 0); var transform = scaleMatrix*rotationMatrix; var start = transform*currentPoint; currentPoint = endPoint; var end = transform*endPoint; Point center; double startAngle; double endAngle; Point axisY; GetArcCenterAndAngles(rx, largeArcFlag, sweepFlag, start, end, out center, out startAngle, out endAngle, out axisY); var inverted = transform.Inverse; center = inverted*center; var rotation = PlaneTransformation.Rotation(xAxisRotation); var axisX = rotation*new Point(rx, 0); axisY = rotation*(axisY/yScale); var ret = new Ellipse(startAngle, endAngle, axisX, axisY, center); Debug.Assert(ApproximateComparer.Close(ret.End, endPoint)); return ret; }
internal void SetTransformOnScaleAndCenter(double scale, Point sourceCenter) { if (OriginalGraph!=null && OriginalGraph.BoundingBox.Diagonal * scale < 5) //less than 5 pixels return; var dx = PanelWidth/2.0 - scale*sourceCenter.X; var dy = PanelHeight/2.0 + scale*sourceCenter.Y; transformation = new PlaneTransformation(scale, 0, dx, 0, -scale, dy); }
static bool HandleTransformIsNotIdentity(GeometryGraph geometryGraph, SugiyamaLayoutSettings sugiyamaLayoutSettings, out PlaneTransformation originalTransform) { var transformIsNotIdentity = !sugiyamaLayoutSettings.Transformation.IsIdentity; originalTransform = sugiyamaLayoutSettings.Transformation; if (transformIsNotIdentity) { var m = sugiyamaLayoutSettings.Transformation.Inverse; foreach (Node n in geometryGraph.Nodes) n.Transform(m); //calculate new label widths and heights foreach (Edge e in geometryGraph.Edges) { if (e.Label != null) { e.OriginalLabelWidth = e.Label.Width; e.OriginalLabelHeight = e.Label.Height; var r = new Rectangle(m*new Point(0, 0), m*new Point(e.Label.Width, e.Label.Height)); e.Label.Width = r.Width; e.Label.Height = r.Height; } } } sugiyamaLayoutSettings.Transformation = PlaneTransformation.UnitTransformation; //restore it later return transformIsNotIdentity; }
///<summary> ///</summary> ///<param name="transformation"></param> public void Transform(PlaneTransformation transformation) { if (BoundaryCurve != null) BoundaryCurve = BoundaryCurve.Transform(transformation); }
void ReadTransform(PlaneTransformation transform) { XmlRead(); if (TokenIs(GeometryToken.Transform)) { XmlRead(); for (int i = 0; i < 2; i++) for (int j = 0; j < 3; j++) { CheckToken(GeometryToken.TransformElement); MoveToContent(); transform[i, j] = ReadElementContentAsDouble(); } XmlRead(); } else { //set the unit transform transform[0, 0] = 1; transform[0, 1] = 0; transform[0, 2] = 0; transform[1, 0] = 0; transform[1, 1] = 1; transform[1, 2] = 0; } }
LayoutAlgorithmSettings ReadSugiyamaLayoutSettings(EdgeRoutingMode edgeRoutingMode) { var sugiyama = new SugiyamaLayoutSettings(); EdgeRoutingSettings routingSettings = sugiyama.EdgeRoutingSettings; routingSettings.EdgeRoutingMode = edgeRoutingMode; LayoutAlgorithmSettings layoutSettings = sugiyama; sugiyama.MinNodeWidth = GetDoubleAttributeOrDefault(GeometryToken.MinNodeWidth, sugiyama.MinNodeWidth); sugiyama.MinNodeHeight = GetDoubleAttributeOrDefault(GeometryToken.MinNodeHeight, sugiyama.MinimalHeight); sugiyama.AspectRatio = GetDoubleAttributeOrDefault(GeometryToken.AspectRatio, sugiyama.AspectRatio); sugiyama.NodeSeparation = GetDoubleAttributeOrDefault(GeometryToken.NodeSeparation, sugiyama.NodeSeparation); sugiyama.ClusterMargin = sugiyama.NodeSeparation; #if REPORTING sugiyama.Reporting = GetBoolAttributeOrDefault(GeometryToken.Reporting, false); #endif sugiyama.RandomSeedForOrdering = GetIntAttributeOrDefault(GeometryToken.RandomSeedForOrdering, sugiyama.RandomSeedForOrdering); sugiyama.NoGainAdjacentSwapStepsBound = GetIntAttributeOrDefault(GeometryToken.NoGainStepsBound, sugiyama.NoGainAdjacentSwapStepsBound); sugiyama.MaxNumberOfPassesInOrdering = GetIntAttributeOrDefault(GeometryToken.MaxNumberOfPassesInOrdering, sugiyama.MaxNumberOfPassesInOrdering); sugiyama.RepetitionCoefficientForOrdering = GetIntAttributeOrDefault(GeometryToken. RepetitionCoefficientForOrdering, sugiyama.RepetitionCoefficientForOrdering); sugiyama.GroupSplit = GetIntAttributeOrDefault(GeometryToken.GroupSplit, sugiyama.GroupSplit); sugiyama.LabelCornersPreserveCoefficient = GetDoubleAttribute(GeometryToken.LabelCornersPreserveCoefficient); sugiyama.BrandesThreshold = GetIntAttributeOrDefault(GeometryToken.BrandesThreshold, sugiyama.BrandesThreshold); sugiyama.LayerSeparation = GetDoubleAttributeOrDefault(GeometryToken.LayerSeparation, sugiyama.LayerSeparation); var transform = new PlaneTransformation(); ReadTransform(transform); return layoutSettings; }
/// <summary> /// Rotate a curve around a given point using radians /// </summary> /// <param name="curve"></param> /// <param name="center"></param> /// <param name="angle"></param> /// <returns></returns> public static ICurve RotateCurveAroundCenterByRadian(ICurve curve, Point center, double angle) { ValidateArg.IsNotNull(curve, "curve"); var c = Math.Cos(angle); var s = Math.Sin(angle); var transform = new PlaneTransformation(1, 0, center.X, 0, 1, center.Y) * new PlaneTransformation(c, -s, 0, s, c, 0) * new PlaneTransformation(1, 0, -center.X, 0, 1, -center.Y); return curve.Transform(transform); }
private static void TransformUnderlyingPolyline(GeometryGraph geometryGraph, GeometryEdge e, PlaneTransformation transformation) { if (e.UnderlyingPolyline != null) { for (Microsoft.Msagl.Core.Geometry.Site s = e.UnderlyingPolyline.HeadSite; s != null; s = s.Next) { s.Point = transformation * s.Point; } } }
void InitiateDrawing() { transformation = null; CalcRects(null); bBNode = null; //to initiate new calculation panel.Invalidate(); }
/// <summary> /// Return the transformed curve /// </summary> /// <param name="transformation"></param> /// <returns>the transformed curve</returns> public ICurve Transform(PlaneTransformation transformation) { return new CubicBezierSegment(transformation * b[0], transformation * b[1], transformation * b[2], transformation * b[3]); }
/// <summary> /// Divid matrix by a matrix /// </summary> /// <param name="transformation0"></param> /// <param name="transformation1"></param> /// <returns></returns> static public PlaneTransformation Divide(PlaneTransformation transformation0, PlaneTransformation transformation1) { return(transformation0 / transformation1); }
void InitTransform() { if (originalGraph == null) { transformation = PlaneTransformation.UnitTransformation; return; } var scale = GetFitScale(); var sourceCenter = originalGraph.BoundingBox.Center; SetTransformOnScaleAndCenter(scale, sourceCenter); }
public void InitTransform() { double mapCenterX = 0.5*_mapWidth; double mapCenterY = 0.5*_mapHeight; double worldCenterX = _bbox.Center.X; double worldCenterY = _bbox.Center.Y; double scaleX = _mapWidth/_bbox.Width; double scaleY = _mapHeight/_bbox.Height; _worldToMap = new PlaneTransformation(scaleX, 0, mapCenterX - scaleX*worldCenterX, 0, scaleY, mapCenterY - scaleY*worldCenterY); _mapToWorld = _worldToMap.Inverse; }
void ToolBarButtonClick(object sender, ToolBarButtonClickEventArgs e) { if (e.Button == zoomin) ZoomInPressed(); else if (e.Button == zoomout) ZoomOutPressed(); else if (e.Button == backwardButton) BackwardButtonPressed(); else if (e.Button == forwardButton) ForwardButtonPressed(); else if (e.Button == saveButton) SaveButtonPressed(); else if (e.Button == print) PrintButtonPressed(); else if (e.Button == openButton) OpenButtonPressed(); else if (e.Button == undoButton) UndoButtonPressed(); else if (e.Button == redoButton) RedoButtonPressed(); else if (e.Button == windowZoomButton) WindowZoomButtonIsPressed(); else if (e.Button == panButton) PanButtonIsPressed(); else if (e.Button == layoutSettingsButton) LayoutSettingsIsClicked(); else if (e.Button == edgeInsertButton) { InsertingEdge = edgeInsertButton.Pushed; if (InsertingEdge) layoutEditor.PrepareForEdgeDragging(); else layoutEditor.ForgetEdgeDragging(); }else if (e.Button == homeZoomButton) { transformation = null; panel.Invalidate(); } }
void SetRenderTransformWithoutRaisingEvents(PlaneTransformation value) { graphCanvas.RenderTransform = new MatrixTransform(value[0, 0], value[0, 1], value[1, 0], value[1, 1], value[0, 2], value[1, 2]); }
/// <summary> /// Return the transformed curve /// </summary> /// <param name="transformation"></param> /// <returns>the transformed curve</returns> public ICurve Transform(PlaneTransformation transformation) { return(new CubicBezierSegment(transformation * b[0], transformation * b[1], transformation * b[2], transformation * b[3])); }
/// <summary> /// Return the transformed curve /// </summary> /// <param name="transformation"></param> /// <returns>the transformed curve</returns> public ICurve Transform(PlaneTransformation transformation) { return new LineSegment(transformation * a, transformation * b); }
/// <summary> /// Transform the curve, arrowheads and label according to the given matrix /// </summary> /// <param name="matrix">affine transform matrix</param> internal void Transform(PlaneTransformation matrix) { if (Curve == null) return; Curve = Curve.Transform(matrix); if (UnderlyingPolyline != null) for (Site s = UnderlyingPolyline.HeadSite, s0 = UnderlyingPolyline.HeadSite; s != null; s = s.Next, s0 = s0.Next) s.Point = matrix * s.Point; var sourceArrow = edgeGeometry.SourceArrowhead; if (sourceArrow != null) sourceArrow.TipPosition = matrix * sourceArrow.TipPosition; var targetArrow = edgeGeometry.TargetArrowhead; if (targetArrow != null) targetArrow.TipPosition = matrix * targetArrow.TipPosition; if (Label != null) Label.Center = matrix * LabelBBox.Center; }
/// <summary> /// Transforms the ellipse /// </summary> /// <param name="transformation"></param> /// <returns>the transformed ellipse</returns> public ICurve Transform(PlaneTransformation transformation){ if(transformation != null){ Point ap = transformation*aAxis - transformation.Offset; Point bp = transformation*bAxis - transformation.Offset; return new Ellipse(parStart, parEnd, ap, bp, transformation*center); } return this; }
/// <summary> /// transforms relative to given rectangles /// </summary> public void TransformRelativeTo(Rectangle oldBounds, Rectangle newBounds) { if (EdgeGeometry != null) { var toOrigin = new PlaneTransformation(1, 0, -oldBounds.Left, 0, 1, -oldBounds.Bottom); var scale = new PlaneTransformation(newBounds.Width/oldBounds.Width, 0, 0, 0,newBounds.Height/oldBounds.Height, 0); var toNewBounds = new PlaneTransformation(1, 0, newBounds.Left, 0, 1, newBounds.Bottom); Transform(toNewBounds*scale*toOrigin); } foreach (var l in this.Labels) { l.Translate(newBounds.LeftBottom - oldBounds.LeftBottom); } }
///<summary> ///</summary> ///<param name="transformation"></param> public void Transform(PlaneTransformation transformation) { BoundaryCurve = BoundaryCurve.Transform(transformation); }
/// <summary> /// Return the transformed curve /// </summary> /// <param name="transformation"></param> /// <returns>the transformed curve</returns> public ICurve Transform(PlaneTransformation transformation) { var bounds = curve.BoundingBox; var lt = transformation * bounds.LeftTop; var rb = transformation * bounds.RightBottom; var transBounds = new Rectangle(lt, rb); return new RoundedRect(transBounds, RadiusX, RadiusY); }