public override void ElementPropertyChanged(ElementPropertyChangedEventArgs e)
        {
            base.ElementPropertyChanged(e);

            if (e.ModelElement == null)
            {
                return;
            }

            if (e.ModelElement.Store.InSerializationTransaction)
            {
                return;
            }

            if (e.ModelElement.IsDeleting || e.ModelElement.IsDeleted)
            {
                return;
            }

            LinkShape linkShape = e.ModelElement as LinkShape;

            if (linkShape != null)
            {
                if (e.DomainProperty.Id == LinkShape.EdgePointsDomainPropertyId)
                {
                    linkShape.UpdateAnchorPlacement();
                }
            }
        }
        protected BaseDiagramItemLinkViewModel(ViewModelStore viewModelStore, DiagramSurfaceViewModel diagram, LinkShape linkShape)
            : base(viewModelStore, diagram, linkShape)
        {
            this.Geometry = ConvertEdgePointsToGeometry(linkShape.EdgePoints);
            this.edgePointsVM = new ObservableCollection<EdgePointViewModel>();

            UpdateEdgePoints();

            Subscribe();
        }
Beispiel #3
0
        private static bool ProcessLinkShape(LinkShape shapeElement, LinkedElementCollection <LinkShapeInfo> infos)
        {
            // try to find NodeShapeInfo for shape element
            LinkShapeInfo info    = null;
            LinkShapeInfo infoAdv = null;

            foreach (LinkShapeInfo i in infos)
            {
                if (i.ElementId == shapeElement.Element.Id)
                {
                    info = i;
                    break;
                }
                else if (shapeElement.Element.GetDomainClass().Id == i.LinkDomainClassId &&
                         shapeElement.FromShape.Element.Id == i.SourceElementId &&
                         shapeElement.ToShape.Element.Id == i.TargetElementId)
                {
                    infoAdv = i;
                }
            }

            if (info == null && infoAdv != null)
            {
                info = infoAdv;
            }

            if (info == null)
            {
                shapeElement.SourceAnchor.DiscardLocationChange = false;
                shapeElement.TargetAnchor.DiscardLocationChange = false;
                return(false);
            }

            shapeElement.SourceAnchor.SetRelativeLocation(info.SourceLocation);
            shapeElement.TargetAnchor.SetRelativeLocation(info.TargetLocation);

            shapeElement.RoutingMode = info.RoutingMode;
            if (info.EdgePoints != null)
            {
                shapeElement.EdgePoints = ConvertFromRelativeEdgePoints(info.EdgePoints, shapeElement.SourceAnchor.AbsoluteLocation);
            }
            else
            {
                shapeElement.EdgePoints.Add(new EdgePoint(shapeElement.SourceAnchor.AbsoluteLocation));
                shapeElement.EdgePoints.Add(new EdgePoint(shapeElement.TargetAnchor.AbsoluteLocation));
            }

            return(true);
        }
Beispiel #4
0
            public void DeleteShapesForElement(Store store, Guid modelElementId)
            {
                List <Guid> shapes = DiagramsShapeStore.GetFromStore(modelElementId);

                if (shapes != null)
                {
                    for (int i = shapes.Count - 1; i >= 0; i--)
                    {
                        LinkShape shape = store.ElementDirectory.FindElement(shapes[i]) as LinkShape;
                        if (shape != null)
                        {
                            shape.Delete();
                        }
                    }
                }
            }
Beispiel #5
0
        public override void ElementAdded(ElementAddedEventArgs e)
        {
            base.ElementAdded(e);

            DiagramHasLinkShapes con = e.ModelElement as DiagramHasLinkShapes;

            if (con != null)
            {
                LinkShape linkShape = con.LinkShape;
                Diagram   diagram   = con.Diagram;

                if (linkShape != null && diagram != null)
                {
                    diagram.RemoveFromShapeMapping(linkShape);
                }
            }
        }
Beispiel #6
0
        public override void ElementAdded(ElementAddedEventArgs e)
        {
            base.ElementAdded(e);

            DiagramHasLinkShapes con = e.ModelElement as DiagramHasLinkShapes;

            if (con != null)
            {
                LinkShape linkShape = con.LinkShape;
                Diagram   diagram   = con.Diagram;

                if (linkShape != null && diagram != null)
                {
                    if (linkShape.IsDeleted)
                    {
                        return;
                    }

                    if (linkShape.SourceAnchor == null || linkShape.TargetAnchor == null)
                    {
                        throw new InvalidOperationException("LinkShape needs to have from and to anchors.");
                    }

                    if (linkShape.SourceAnchor.FromShape == null || linkShape.TargetAnchor.ToShape == null)
                    {
                        throw new InvalidOperationException("LinkShape anchors need to have from and to shape.");
                    }

                    diagram.AddToShapeMapping(linkShape);

                    if (linkShape.EdgePoints.Count == 0)
                    {
                        linkShape.Layout(FixedGeometryPoints.None);
                    }
                    else
                    {
                        linkShape.UpdateLinkPlacement();

                        if (!con.Store.InSerializationTransaction)
                        {
                            linkShape.Layout(FixedGeometryPoints.SourceAndTarget);
                        }
                    }
                }
            }
        }
        /// <summary>
        /// Write all properties that need to be serialized as XML attributes.
        /// </summary>
        /// <param name="serializationContext">Serialization context.</param>
        /// <param name="element">LinkShape instance to be serialized.</param>
        /// <param name="writer">XmlWriter to write serialized data to.</param>
        protected override void WritePropertiesAsAttributes(Microsoft.VisualStudio.Modeling.SerializationContext serializationContext, Microsoft.VisualStudio.Modeling.ModelElement element, System.Xml.XmlWriter writer)
        {
            base.WritePropertiesAsAttributes(serializationContext, element, writer);

            LinkShape instanceOfLinkShape = element as LinkShape;

            global::System.Diagnostics.Debug.Assert(instanceOfLinkShape != null, "Expecting an instance of LinkShape");

            if (!serializationContext.Result.Failed)
            {
                string serializedPropValue = SerializationUtilities.GetString <Guid>(serializationContext, instanceOfLinkShape.SourceAnchor.FromShape.Id);
                DiagramsDSLSerializationHelper.Instance.WriteAttributeString(serializationContext, element, writer, "sourceShapeId", serializedPropValue);

                serializedPropValue = SerializationUtilities.GetString <Guid>(serializationContext, instanceOfLinkShape.TargetAnchor.ToShape.Id);
                DiagramsDSLSerializationHelper.Instance.WriteAttributeString(serializationContext, element, writer, "targetShapeId", serializedPropValue);
            }
        }
        /// <summary>
        /// This method deserializes all properties that are serialized as XML attributes.
        /// </summary>
        /// <remarks>
        /// Because this method only handles properties serialized as XML attributes, the passed-in reader shouldn't be moved inside this method.
        /// The caller will guarantee that the reader is positioned on the open XML tag of the current element being deserialized.
        /// </remarks>
        /// <param name="serializationContext">Serialization context.</param>
        /// <param name="element">In-memory LinkShape instance that will get the deserialized data.</param>
        /// <param name="reader">XmlReader to read serialized data from.</param>
        protected override void ReadPropertiesFromAttributes(SerializationContext serializationContext, ModelElement element, System.Xml.XmlReader reader)
        {
            LinkShape instanceOfLinkShape = element as LinkShape;

            global::System.Diagnostics.Debug.Assert(instanceOfLinkShape != null, "Expecting an instance of LinkShape");

            // DummyProperty
            if (!serializationContext.Result.Failed)
            {
                string attribDummyProperty = DiagramsDSLSerializationHelper.Instance.ReadAttribute(serializationContext, element, reader, "dummyProperty");
                if (attribDummyProperty != null)
                {
                    global::System.String valueOfDummyProperty;
                    if (SerializationUtilities.TryGetValue <global::System.String>(serializationContext, attribDummyProperty, out valueOfDummyProperty))
                    {
                        instanceOfLinkShape.DummyProperty = valueOfDummyProperty;
                    }
                    else
                    {   // Invalid property value, ignored.
                        TestDslDefinitionSerializationBehaviorSerializationMessages.IgnoredPropertyValue(serializationContext, reader, "dummyProperty", typeof(global::System.String), attribDummyProperty);
                    }
                }
            }
            // RoutingMode
            if (!serializationContext.Result.Failed)
            {
                string attribRoutingMode = DiagramsDSLSerializationHelper.Instance.ReadAttribute(serializationContext, element, reader, "routingMode");
                if (attribRoutingMode != null)
                {
                    RoutingMode valueOfRoutingMode;
                    if (SerializationUtilities.TryGetValue <RoutingMode>(serializationContext, attribRoutingMode, out valueOfRoutingMode))
                    {
                        instanceOfLinkShape.RoutingMode = valueOfRoutingMode;
                    }
                    else
                    {   // Invalid property value, ignored.
                        TestDslDefinitionSerializationBehaviorSerializationMessages.IgnoredPropertyValue(serializationContext, reader, "routingMode", typeof(RoutingMode), attribRoutingMode);
                    }
                }
            }
            //base.ReadPropertiesFromAttributes(serializationContext, element, reader);
        }
            public virtual void AddRSShapesForElement(DomainModelElement sourceElement, DomainModelElement targetElement, ModelElement con, Guid shapeType)
            {
                List <Guid> shapeIdsSource = DiagramsShapeStore.GetFromStore(sourceElement.Id);
                List <Guid> shapeIdsTarget = DiagramsShapeStore.GetFromStore(targetElement.Id);

                if (shapeIdsSource == null || shapeIdsTarget == null)
                {
                    return;
                }
                if (shapeIdsSource.Count == 0 || shapeIdsTarget.Count == 0)
                {
                    return;
                }

                IDomainModelServices topMost = sourceElement.GetDomainModelServices().TopMostService;

                foreach (Guid sourceShapeId in shapeIdsSource)
                {
                    NodeShape sourceShape = con.Store.ElementDirectory.FindElement(sourceShapeId) as NodeShape;
                    if (sourceShape == null)
                    {
                        continue;
                    }
                    foreach (Guid targetShapeId in shapeIdsTarget)
                    {
                        NodeShape targetShape = con.Store.ElementDirectory.FindElement(targetShapeId) as NodeShape;
                        if (targetShape != null)
                        {
                            if (sourceShape.Diagram == targetShape.Diagram)
                            {
                                if (!DiagramHelper.IsLinkDisplayedOn(sourceShape.Diagram, shapeType, con.Id, sourceShape.Id, targetShape.Id))
                                {
                                    LinkShape shape = topMost.ShapeProvider.CreateShapeForElementLink(shapeType, con, sourceShape, targetShape) as LinkShape;
                                    sourceShape.Diagram.LinkShapes.Add(shape);
                                    shape.Layout(FixedGeometryPoints.None);
                                }
                            }
                        }
                    }
                }
            }
Beispiel #10
0
        /// <summary>
        /// Updates the position of a link shape.
        /// </summary>
        /// <param name="linkShape">Link shape.</param>
        /// <param name="shape">Graphical dependency shape.</param>
        /// <param name="mainShape">Node shape.</param>
        /// <param name="bSource">True if graphical dependency shape is source.</param>
        public void UpdateLinkShapePosition(LinkShape linkShape, GraphicalDependencyShape shape, NodeShape mainShape, bool bSource)
        {
            if (linkShape == null)
            {
                return;
            }

            if (bSource)
            {
                linkShape.SourceAnchor.AbsoluteLocation = new PointD(shape.AbsoluteBounds.Right + LinkAnchorMargin, shape.AbsoluteBounds.Center.Y);
                linkShape.TargetAnchor.AbsoluteLocation = new PointD(mainShape.AbsoluteBounds.Left - LinkAnchorMargin, mainShape.AbsoluteBounds.Center.Y);
                linkShape.Layout(FixedGeometryPoints.SourceAndTarget);
            }
            else
            {
                linkShape.SourceAnchor.AbsoluteLocation = new PointD(mainShape.AbsoluteBounds.Right + LinkAnchorMargin, mainShape.AbsoluteBounds.Center.Y);
                linkShape.TargetAnchor.AbsoluteLocation = new PointD(shape.AbsoluteBounds.Left - LinkAnchorMargin, shape.AbsoluteBounds.Center.Y);
                linkShape.Layout(FixedGeometryPoints.SourceAndTarget);
            }

            /*
             * if (bSource)
             * {
             *  linkShape.SourceAnchor.AbsoluteLocation = LinkShape.CalculateLocation(
             *      LinkPlacement.Right, shape.AbsoluteBounds, new PointD(shape.AbsoluteBounds.Right + LinkAnchorMargin, shape.AbsoluteBounds.Center.Y));
             *  linkShape.TargetAnchor.AbsoluteLocation = LinkShape.CalculateLocation(
             *      LinkPlacement.Left, mainShape.AbsoluteBounds, new PointD(mainShape.AbsoluteBounds.Left - LinkAnchorMargin, mainShape.AbsoluteBounds.Center.Y));
             * }
             * else
             * {
             *  linkShape.SourceAnchor.AbsoluteLocation = LinkShape.CalculateLocation(LinkPlacement.Right,
             *      mainShape.AbsoluteBounds, new PointD(mainShape.AbsoluteBounds.Right + LinkAnchorMargin, mainShape.AbsoluteBounds.Center.Y));
             *  linkShape.TargetAnchor.AbsoluteLocation = LinkShape.CalculateLocation(LinkPlacement.Left, shape.AbsoluteBounds,
             *      new PointD(shape.AbsoluteBounds.Left - LinkAnchorMargin, shape.AbsoluteBounds.Center.Y));
             * }
             */
        }
Beispiel #11
0
        public override void ElementPropertyChanged(ElementPropertyChangedEventArgs e)
        {
            base.ElementPropertyChanged(e);

            if (e.ModelElement == null)
            {
                return;
            }

            if (e.ModelElement.Store.InSerializationTransaction)
            {
                return;
            }

            LinkShape linkShape = e.ModelElement as LinkShape;

            if (linkShape != null)
            {
                if (e.DomainProperty.Id == LinkShape.RoutingModeDomainPropertyId)
                {
                    linkShape.Layout(FixedGeometryPoints.SourceAndTarget);
                }
            }
        }
Beispiel #12
0
        /// <summary>
        /// Corret link shapes placement.
        /// </summary>
        /// <param name="sizeOld"></param>
        /// <param name="sizeNew"></param>
        internal void CorrectLinkShapesOnSizeChanged(SizeD sizeOld, SizeD sizeNew)
        {
            // List<LinkShape> shapesToLayout = new List<LinkShape>();

            double widthChange  = (sizeNew.Width - sizeOld.Width);
            double heightChange = (sizeNew.Height - sizeOld.Height);

            double widthFactor  = sizeNew.Width / sizeOld.Width;
            double heightFactor = sizeNew.Height / sizeOld.Height;

            foreach (SourceAnchor anchor in this.SourceAnchors)
            {
                if (anchor.FromShape == null)
                {
                    continue;
                }

                if (anchor.IsDeleted || anchor.IsDeleting)
                {
                    continue;
                }

                NodeShape shape     = anchor.FromShape;
                LinkShape linkShape = anchor.LinkShape;

                double newLeft = (anchor.AbsoluteLocation.X - shape.AbsoluteLocation.X) * widthFactor + shape.AbsoluteLocation.X;
                double newTop  = (anchor.AbsoluteLocation.Y - shape.AbsoluteLocation.Y) * heightFactor + shape.AbsoluteLocation.Y;

                if (linkShape.LinkPlacementStart == LinkPlacement.Bottom)
                {
                    anchor.AbsoluteLocation = new PointD(newLeft, anchor.AbsoluteLocation.Y + heightChange);
                }
                else if (linkShape.LinkPlacementStart == LinkPlacement.Top)
                {
                    anchor.AbsoluteLocation = new PointD(newLeft, anchor.AbsoluteLocation.Y);
                }
                else if (linkShape.LinkPlacementStart == LinkPlacement.Right)
                {
                    anchor.AbsoluteLocation = new PointD(anchor.AbsoluteLocation.X + widthChange, newTop);
                }
                else if (linkShape.LinkPlacementStart == LinkPlacement.Left)
                {
                    anchor.AbsoluteLocation = new PointD(anchor.AbsoluteLocation.X, newTop);
                }

                //if (!shapesToLayout.Contains(anchor.LinkShape))
                //    shapesToLayout.Add(anchor.LinkShape);
            }

            foreach (TargetAnchor anchor in this.TargetAnchors)
            {
                if (anchor.ToShape == null)
                {
                    continue;
                }

                if (anchor.IsDeleted || anchor.IsDeleting)
                {
                    continue;
                }

                NodeShape shape     = anchor.ToShape;
                LinkShape linkShape = anchor.LinkShape;

                double newLeft = (anchor.AbsoluteLocation.X - shape.AbsoluteLocation.X) * widthFactor + shape.AbsoluteLocation.X;
                double newTop  = (anchor.AbsoluteLocation.Y - shape.AbsoluteLocation.Y) * heightFactor + shape.AbsoluteLocation.Y;

                if (linkShape.LinkPlacementEnd == LinkPlacement.Bottom)
                {
                    anchor.AbsoluteLocation = new PointD(newLeft, anchor.AbsoluteLocation.Y + heightChange);
                }
                else if (linkShape.LinkPlacementEnd == LinkPlacement.Top)
                {
                    anchor.AbsoluteLocation = new PointD(newLeft, anchor.AbsoluteLocation.Y);
                }
                else if (linkShape.LinkPlacementEnd == LinkPlacement.Right)
                {
                    anchor.AbsoluteLocation = new PointD(anchor.AbsoluteLocation.X + widthChange, newTop);
                }
                else if (linkShape.LinkPlacementEnd == LinkPlacement.Left)
                {
                    anchor.AbsoluteLocation = new PointD(anchor.AbsoluteLocation.X, newTop);
                }

                //if (!shapesToLayout.Contains(anchor.LinkShape))
                //   shapesToLayout.Add(anchor.LinkShape);
            }

            //foreach (LinkShape s in shapesToLayout)
            //    s.Layout(FixedGeometryPoints.SourceAndTarget);
        }
		private static void WriteChildElements(DslModeling::SerializationContext serializationContext, LinkShape element, global::System.Xml.XmlWriter writer)
		{
			// LinkShapeHasSourceAnchor
			LinkShapeHasSourceAnchor theLinkShapeHasSourceAnchorInstance = LinkShapeHasSourceAnchor.GetLinkToSourceAnchor(element);
			if (!serializationContext.Result.Failed && theLinkShapeHasSourceAnchorInstance != null)
			{
				writer.WriteStartElement("sourceAnchor");
				DslModeling::DomainClassXmlSerializer relSerializer = serializationContext.Directory.GetSerializer(theLinkShapeHasSourceAnchorInstance.GetDomainClass().Id);
				global::System.Diagnostics.Debug.Assert(relSerializer != null, "Cannot find serializer for " + theLinkShapeHasSourceAnchorInstance.GetDomainClass().Name + "!");
				relSerializer.Write(serializationContext, theLinkShapeHasSourceAnchorInstance, writer);
				writer.WriteEndElement();
			}
	
			// LinkShapeHasTargetAnchor
			LinkShapeHasTargetAnchor theLinkShapeHasTargetAnchorInstance = LinkShapeHasTargetAnchor.GetLinkToTargetAnchor(element);
			if (!serializationContext.Result.Failed && theLinkShapeHasTargetAnchorInstance != null)
			{
				writer.WriteStartElement("targetAnchor");
				DslModeling::DomainClassXmlSerializer relSerializer = serializationContext.Directory.GetSerializer(theLinkShapeHasTargetAnchorInstance.GetDomainClass().Id);
				global::System.Diagnostics.Debug.Assert(relSerializer != null, "Cannot find serializer for " + theLinkShapeHasTargetAnchorInstance.GetDomainClass().Name + "!");
				relSerializer.Write(serializationContext, theLinkShapeHasTargetAnchorInstance, writer);
				writer.WriteEndElement();
			}
	
		}
		/// <summary>
		/// This method deserializes all child model elements.
		/// </summary>
		/// <remarks>
		/// The caller will position the reader at the open tag of the first child XML element to deserialized.
		/// This method will read as many child elements as it can. It returns under three circumstances:
		/// 1) When an unknown child XML element is encountered. In this case, this method will position the reader at the 
		///    open tag of the unknown element. This implies that if the first child XML element is unknown, this method 
		///    should return immediately and do nothing.
		/// 2) When all child XML elemnets are read. In this case, the reader will be positioned at the end tag of the parent element.
		/// 3) EOF.
		/// </remarks>
		/// <param name="serializationContext">Serialization context.</param>
		/// <param name="reader">XmlReader to read serialized data from.</param>
		/// <param name="element">In-memory LinkShape instance that will get the deserialized data.</param>
		private static void ReadChildElements(DslModeling::SerializationContext serializationContext, LinkShape element, global::System.Xml.XmlReader reader)
		{
			while (!serializationContext.Result.Failed && !reader.EOF && reader.NodeType == global::System.Xml.XmlNodeType.Element)
			{
				switch (reader.LocalName)
				{
					case "sourceAnchor":	// Relationship "LinkShapeHasSourceAnchor"
						if (reader.IsEmptyElement)
						{	// No instance of this relationship, just skip
							DslModeling::SerializationUtilities.Skip(reader);
						}
						else
						{
							DslModeling::SerializationUtilities.SkipToFirstChild(reader);  // Skip the open tag of <sourceAnchor>
							ReadLinkShapeHasSourceAnchorInstance(serializationContext, element, reader);
							DslModeling::SerializationUtilities.Skip(reader);  // Skip the close tag of </sourceAnchor>
						}
						break;
					case "targetAnchor":	// Relationship "LinkShapeHasTargetAnchor"
						if (reader.IsEmptyElement)
						{	// No instance of this relationship, just skip
							DslModeling::SerializationUtilities.Skip(reader);
						}
						else
						{
							DslModeling::SerializationUtilities.SkipToFirstChild(reader);  // Skip the open tag of <targetAnchor>
							ReadLinkShapeHasTargetAnchorInstance(serializationContext, element, reader);
							DslModeling::SerializationUtilities.Skip(reader);  // Skip the close tag of </targetAnchor>
						}
						break;
					default:
						return;  // Don't know this element.
				}
			}
		}
		public static void SetTargetAnchor(LinkShape element, TargetAnchor newTargetAnchor)
		{
			DslModeling::DomainRoleInfo.SetLinkedElement(element, LinkShapeDomainRoleId, newTargetAnchor);
		}
		public static TargetAnchor GetTargetAnchor(LinkShape element)
		{
			return DslModeling::DomainRoleInfo.GetLinkedElement(element, LinkShapeDomainRoleId) as TargetAnchor;
		}
		public static void SetLinkShape(TargetAnchor element, LinkShape newLinkShape)
		{
			DslModeling::DomainRoleInfo.SetLinkedElement(element, TargetAnchorDomainRoleId, newLinkShape);
		}
		/// <summary>
		/// Constructor
		/// Creates a LinkShapeHasTargetAnchor link in the same Partition as the given LinkShape
		/// </summary>
		/// <param name="source">LinkShape to use as the source of the relationship.</param>
		/// <param name="target">TargetAnchor to use as the target of the relationship.</param>
		public LinkShapeHasTargetAnchor(LinkShape source, TargetAnchor target)
			: base((source != null ? source.Partition : null), new DslModeling::RoleAssignment[]{new DslModeling::RoleAssignment(LinkShapeHasTargetAnchor.LinkShapeDomainRoleId, source), new DslModeling::RoleAssignment(LinkShapeHasTargetAnchor.TargetAnchorDomainRoleId, target)}, null)
		{
		}
		public static void SetSourceAnchor(LinkShape element, SourceAnchor newSourceAnchor)
		{
			DslModeling::DomainRoleInfo.SetLinkedElement(element, LinkShapeDomainRoleId, newSourceAnchor);
		}
		public static SourceAnchor GetSourceAnchor(LinkShape element)
		{
			return DslModeling::DomainRoleInfo.GetLinkedElement(element, LinkShapeDomainRoleId) as SourceAnchor;
		}
        /// <summary>
        /// Updates the position of a link shape.
        /// </summary>
        /// <param name="linkShape">Link shape.</param>
        /// <param name="shape">Graphical dependency shape.</param>
        /// <param name="mainShape">Node shape.</param>
        /// <param name="bSource">True if graphical dependency shape is source.</param>
        public void UpdateLinkShapePosition(LinkShape linkShape, GraphicalDependencyShape shape, NodeShape mainShape, bool bSource)
        {
            if (linkShape == null)
                return;

            if (bSource)
            {
                linkShape.SourceAnchor.AbsoluteLocation = new PointD(shape.AbsoluteBounds.Right + LinkAnchorMargin, shape.AbsoluteBounds.Center.Y);
                linkShape.TargetAnchor.AbsoluteLocation = new PointD(mainShape.AbsoluteBounds.Left - LinkAnchorMargin, mainShape.AbsoluteBounds.Center.Y);
                linkShape.Layout(FixedGeometryPoints.SourceAndTarget);
            }
            else
            {
                linkShape.SourceAnchor.AbsoluteLocation = new PointD(mainShape.AbsoluteBounds.Right + LinkAnchorMargin, mainShape.AbsoluteBounds.Center.Y);
                linkShape.TargetAnchor.AbsoluteLocation = new PointD(shape.AbsoluteBounds.Left - LinkAnchorMargin, shape.AbsoluteBounds.Center.Y);
                linkShape.Layout(FixedGeometryPoints.SourceAndTarget);
            }

            /*
            if (bSource)
            {
                linkShape.SourceAnchor.AbsoluteLocation = LinkShape.CalculateLocation(
                    LinkPlacement.Right, shape.AbsoluteBounds, new PointD(shape.AbsoluteBounds.Right + LinkAnchorMargin, shape.AbsoluteBounds.Center.Y));
                linkShape.TargetAnchor.AbsoluteLocation = LinkShape.CalculateLocation(
                    LinkPlacement.Left, mainShape.AbsoluteBounds, new PointD(mainShape.AbsoluteBounds.Left - LinkAnchorMargin, mainShape.AbsoluteBounds.Center.Y));
            }
            else
            {
                linkShape.SourceAnchor.AbsoluteLocation = LinkShape.CalculateLocation(LinkPlacement.Right,
                    mainShape.AbsoluteBounds, new PointD(mainShape.AbsoluteBounds.Right + LinkAnchorMargin, mainShape.AbsoluteBounds.Center.Y));
                linkShape.TargetAnchor.AbsoluteLocation = LinkShape.CalculateLocation(LinkPlacement.Left, shape.AbsoluteBounds,
                    new PointD(shape.AbsoluteBounds.Left - LinkAnchorMargin, shape.AbsoluteBounds.Center.Y));
            }
            */
        }
 /// <summary>
 /// Creates the view model for the given link shape.
 /// </summary>
 /// <param name="nodeShapeType">Shape type for which the view model is to be created.</param>
 /// <param name="diagram">Diagram surface vm.</param>
 /// <param name="nodeShape">Link shape.</param>
 /// <returns>
 /// View model of type BaseDiagramItemLinkViewModel if a view model can be created for the given element. Null otherwise.</returns>
 public abstract BaseDiagramItemLinkViewModel CreateDiagramLinkViewModel(Guid nodeShapeType, DiagramSurfaceViewModel diagram, LinkShape nodeShape);
		/// <summary>
		/// Constructor
		/// Creates a DiagramHasLinkShapes link in the same Partition as the given Diagram
		/// </summary>
		/// <param name="source">Diagram to use as the source of the relationship.</param>
		/// <param name="target">LinkShape to use as the target of the relationship.</param>
		public DiagramHasLinkShapes(Diagram source, LinkShape target)
			: base((source != null ? source.Partition : null), new DslModeling::RoleAssignment[]{new DslModeling::RoleAssignment(DiagramHasLinkShapes.DiagramDomainRoleId, source), new DslModeling::RoleAssignment(DiagramHasLinkShapes.LinkShapeDomainRoleId, target)}, null)
		{
		}
		private static void ReadPropertiesFromElements(DslModeling::SerializationContext serializationContext, LinkShape element, global::System.Xml.XmlReader reader)
		{
			while (!serializationContext.Result.Failed && !reader.EOF && reader.NodeType == global::System.Xml.XmlNodeType.Element)
			{
				switch (reader.LocalName)
				{
					case "edgePoints":	// EdgePoints
						if (reader.IsEmptyElement)
						{	// No serialized value, must be default one.
							DslModeling::SerializationUtilities.Skip(reader);  // Skip this tag.
						}
						else
						{
							string strEdgePoints = DiagramsDSLSerializationHelper.Instance.ReadElementContentAsString(serializationContext, element, reader);
							EdgePointCollection valueOfEdgePoints;
							if (DslModeling::SerializationUtilities.TryGetValue<EdgePointCollection>(serializationContext, strEdgePoints, out valueOfEdgePoints))
							{
								element.EdgePoints = valueOfEdgePoints;
							}
							else
							{	// Invalid property value, ignored.
								TestDslDefinitionSerializationBehaviorSerializationMessages.IgnoredPropertyValue(serializationContext, reader, "edgePoints", typeof(EdgePointCollection), strEdgePoints);
							}
	
							DslModeling::SerializationUtilities.SkipToNextElement(reader);
						}
						break;
					default:
						return;  // Don't know this element.
				}
			}
		}
		/// <summary>
		/// Reads instance of relationship LinkShapeHasTargetAnchor.
		/// </summary>
		/// <remarks>
		/// The caller will position the reader at the open tag of the first XML element inside the relationship tag, so it can be
		/// either the first instance, or a bogus tag. This method will deserialize only the first valid instance and ignore all the
		/// rest tags (because the multiplicity allows only one instance). When the method returns, the reader will be positioned at 
		/// the end tag of the relationship (or EOF if somehow that happens).
		/// </remarks>
		/// <param name="serializationContext">Serialization context.</param>
		/// <param name="element">In-memory LinkShape instance that will get the deserialized data.</param>
		/// <param name="reader">XmlReader to read serialized data from.</param>
		private static void ReadLinkShapeHasTargetAnchorInstance(DslModeling::SerializationContext serializationContext, LinkShape element, global::System.Xml.XmlReader reader)
		{
			if (DslModeling::DomainRoleInfo.GetElementLinks<LinkShapeHasTargetAnchor> (element, LinkShapeHasTargetAnchor.LinkShapeDomainRoleId).Count > 0)
			{	// Only allow one instance, which already exists, so skip everything
				DslModeling::SerializationUtilities.Skip(reader);	// Moniker contains no child XML elements, so just skip.
				return;
			}
	
			while (!serializationContext.Result.Failed && !reader.EOF && reader.NodeType == global::System.Xml.XmlNodeType.Element)
			{
				DslModeling::DomainClassXmlSerializer newLinkShapeHasTargetAnchorSerializer = serializationContext.Directory.GetSerializer(LinkShapeHasTargetAnchor.DomainClassId);
				global::System.Diagnostics.Debug.Assert(newLinkShapeHasTargetAnchorSerializer != null, "Cannot find serializer for LinkShapeHasTargetAnchor!");
				LinkShapeHasTargetAnchor newLinkShapeHasTargetAnchor = newLinkShapeHasTargetAnchorSerializer.TryCreateInstance (serializationContext, reader, element.Partition) as LinkShapeHasTargetAnchor;
				if (newLinkShapeHasTargetAnchor != null)
				{
					DslModeling::DomainRoleInfo.SetRolePlayer (newLinkShapeHasTargetAnchor, LinkShapeHasTargetAnchor.LinkShapeDomainRoleId, element);
					DslModeling::DomainClassXmlSerializer targetSerializer = serializationContext.Directory.GetSerializer (newLinkShapeHasTargetAnchor.GetDomainClass().Id);	
					global::System.Diagnostics.Debug.Assert (targetSerializer != null, "Cannot find serializer for " + newLinkShapeHasTargetAnchor.GetDomainClass().Name + "!");
					targetSerializer.Read(serializationContext, newLinkShapeHasTargetAnchor, reader);
					break;	// Only allow one instance.
				}
				else
				{	// Maybe the relationship is serialized in short-form by mistake.
					DslModeling::DomainClassXmlSerializer newTargetAnchorOfLinkShapeHasTargetAnchorSerializer = serializationContext.Directory.GetSerializer(TargetAnchor.DomainClassId);
					global::System.Diagnostics.Debug.Assert(newTargetAnchorOfLinkShapeHasTargetAnchorSerializer != null, "Cannot find serializer for TargetAnchor!");
					TargetAnchor newTargetAnchorOfLinkShapeHasTargetAnchor = newTargetAnchorOfLinkShapeHasTargetAnchorSerializer.TryCreateInstance(serializationContext, reader, element.Partition) as TargetAnchor;
					if (newTargetAnchorOfLinkShapeHasTargetAnchor != null)
					{
						TestDslDefinitionSerializationBehaviorSerializationMessages.ExpectingFullFormRelationship(serializationContext, reader, typeof(LinkShapeHasTargetAnchor));
						element.TargetAnchor = newTargetAnchorOfLinkShapeHasTargetAnchor;
						DslModeling::DomainClassXmlSerializer targetSerializer = serializationContext.Directory.GetSerializer (newTargetAnchorOfLinkShapeHasTargetAnchor.GetDomainClass().Id);	
						global::System.Diagnostics.Debug.Assert (targetSerializer != null, "Cannot find serializer for " + newTargetAnchorOfLinkShapeHasTargetAnchor.GetDomainClass().Name + "!");
						targetSerializer.Read(serializationContext, newTargetAnchorOfLinkShapeHasTargetAnchor, reader);
						break;	// Only allow one instance.
					}
					else
					{	// Unknown element, skip.
						DslModeling::SerializationUtilities.Skip(reader);
					}
				}
			}
		}
		public static Diagram GetDiagram(LinkShape element)
		{
			return DslModeling::DomainRoleInfo.GetLinkedElement(element, LinkShapeDomainRoleId) as Diagram;
		}
		private static void WritePropertiesAsElements(DslModeling::SerializationContext serializationContext, LinkShape element, global::System.Xml.XmlWriter writer)
		{
			// EdgePoints
			if (!serializationContext.Result.Failed)
			{
				EdgePointCollection propValue = element.EdgePoints;
				string serializedPropValue = DslModeling::SerializationUtilities.GetString<EdgePointCollection>(serializationContext, propValue);
				if (!serializationContext.Result.Failed)
				{
				DiagramsDSLSerializationHelper.Instance.WriteElementString(serializationContext, element, writer, "edgePoints", serializedPropValue);
				}
			}
		} 
        private static bool ProcessLinkShape(LinkShape shapeElement, LinkedElementCollection<LinkShapeInfo> infos)
        {
            // try to find NodeShapeInfo for shape element
            LinkShapeInfo info = null;
            LinkShapeInfo infoAdv = null;
            foreach (LinkShapeInfo i in infos)
            {
                if (i.ElementId == shapeElement.Element.Id)
                {
                    info = i;
                    break;
                }
                else if( shapeElement.Element.GetDomainClass().Id == i.LinkDomainClassId &&
                    shapeElement.FromShape.Element.Id == i.SourceElementId && 
                    shapeElement.ToShape.Element.Id == i.TargetElementId )
                {
                    infoAdv = i;
                }
            }

            if (info == null && infoAdv != null)
                info = infoAdv;

            if (info == null)
            {
                shapeElement.SourceAnchor.DiscardLocationChange = false;
                shapeElement.TargetAnchor.DiscardLocationChange = false;
                return false;
            }

            shapeElement.SourceAnchor.SetRelativeLocation(info.SourceLocation);
            shapeElement.TargetAnchor.SetRelativeLocation(info.TargetLocation);

            shapeElement.RoutingMode = info.RoutingMode;
            if (info.EdgePoints != null)
                shapeElement.EdgePoints = ConvertFromRelativeEdgePoints(info.EdgePoints, shapeElement.SourceAnchor.AbsoluteLocation);
            else
            {
                shapeElement.EdgePoints.Add(new EdgePoint(shapeElement.SourceAnchor.AbsoluteLocation));
                shapeElement.EdgePoints.Add(new EdgePoint(shapeElement.TargetAnchor.AbsoluteLocation));
            }

            return true;
        }
		public static void SetDiagram(LinkShape element, Diagram newDiagram)
		{
			DslModeling::DomainRoleInfo.SetLinkedElement(element, LinkShapeDomainRoleId, newDiagram);
		}