/// <summary>
 /// An IMS event to track the shape element added to the associated
 /// diagram during this connect action.
 /// </summary>
 /// <param name="sender"></param>
 /// <param name="e"></param>
 private void InternalConstraintAddedEvent(object sender, ElementAddedEventArgs e)
 {
     if (myAddedConstraint == null)
     {
         UniquenessConstraint candidate = e.ModelElement as UniquenessConstraint;
         if (candidate != null && candidate.IsInternal)
         {
             ORMDiagram d = Diagram as ORMDiagram;
             if (d != null)
             {
                 // Find the shape associated with the fact type we added to
                 LinkedElementCollection <FactType> candidateFacts = candidate.FactTypeCollection;
                 if (candidateFacts.Count != 0)
                 {
                     FactTypeShape shape = d.FindShapeForElement(candidateFacts[0]) as FactTypeShape;
                     if (shape != null)
                     {
                         myDropTargetShape = shape;
                         myAddedConstraint = candidate;
                     }
                 }
             }
         }
     }
 }
        public void ExactlyOneTest_1b(Store store)
        {
            myTestServices.LogValidationErrors("No errors expected");
            ORMModel            model      = store.ElementDirectory.FindElements <ORMModel>()[0];
            FrequencyConstraint constraint = (FrequencyConstraint)model.ConstraintsDictionary.GetElement("FrequencyConstraint1").SingleElement;

            // DomainTypeDescriptor.CreatePropertyDescriptor(constraint, FrequencyConstraint.MaxFrequencyDomainPropertyId).SetValue(constraint, 1);
            myTestServices.LogValidationErrors("Introduce Error[FrequencyConstraintExactlyOneError]");
            using (Transaction t = store.TransactionManager.BeginTransaction("Read the error"))
            {
                constraint.MinFrequency = 1;
                constraint.MaxFrequency = 1;
                t.Commit();
            }
            myTestServices.LogValidationErrors("Fixing error with error activation service");
            ((IORMToolServices)store).ModelErrorActivationService.ActivateError(constraint, constraint.FrequencyConstraintExactlyOneError);
            myTestServices.LogValidationErrors("[FrequencyConstraintExactlyOneError] removed, different error introduced. Removing new error");

            // Deleting one of the two uniqnuess constraints...
            UniquenessConstraint uniqueC = (UniquenessConstraint)model.ConstraintsDictionary.GetElement("InternalUniquenessConstraint5").SingleElement;

            using (Transaction t = store.TransactionManager.BeginTransaction("Read the error"))
            {
                uniqueC.Delete();
                t.Commit();
            }
            myTestServices.LogValidationErrors("All errors resolved");
        }
Exemple #3
0
 public IEnumerable<ErrorMessage> Validate(WineDTO wine)
 {
     var entity = wine.To();
     var validator = new ValidateWine(entity.Name, entity.Kind.ToMaybe(), entity.Producer.ToMaybe(), entity.Alcohol);
     var uniqueness = new UniquenessConstraint<Wine>(() => validator.Commit());
     return validator.Errors.Union(uniqueness.Errors);
 }
        /// <summary>
        /// Set this mouse action as the active action on the
        /// diagram of the given shape.
        /// </summary>
        /// <param name="attachToShape">The shape the constraint is being attached to.</param>
        /// <param name="constraint">The constraint being connected.</param>
        /// <param name="clientView">The active DiagramClientView</param>
        public void ChainMouseAction(FactTypeShape attachToShape, UniquenessConstraint constraint, DiagramClientView clientView)
        {
            DiagramView activeView = Diagram.ActiveDiagramView;

            if (activeView != null)
            {
                // Move on to the selection action
                clientView.ActiveMouseAction = this;

                // Now emulate a mouse click in the middle of the added constraint. The click
                // actions provide a starting point for the connect action, so a mouse move
                // provides a drag line.
                Point emulateClickPoint = clientView.WorldToDevice(attachToShape.GetAbsoluteConstraintAttachPoint(constraint, FactSetConstraint.GetLink(constraint, attachToShape.AssociatedFactType)));
                DiagramMouseEventArgs mouseEventArgs = new DiagramMouseEventArgs(new MouseEventArgs(MouseButtons.Left, 1, emulateClickPoint.X, emulateClickPoint.Y, 0), clientView);
                MouseDown(mouseEventArgs);
                Click(new DiagramPointEventArgs(emulateClickPoint.X, emulateClickPoint.Y, PointRelativeTo.Client, clientView));
                MouseUp(mouseEventArgs);
                attachToShape.Invalidate(true);

                // An extra move lets us chain when the mouse is not on the design surface,
                // such as when we are being activated via the task list.
                MouseMove(mouseEventArgs);

                ORMDiagram.SelectToolboxItem(activeView, ResourceStrings.ToolboxInternalUniquenessConstraintItemId);
                FactTypeShape.ActiveInternalUniquenessConstraintConnectAction = this;
            }
        }
 public IEnumerable<ErrorMessage> Validate(ProducerDTO producer)
 {
     var entity = producer.To();
     var validator = new ValidateProducer(entity.Name);
     var uniqueness = new UniquenessConstraint<Producer>(() => validator.Commit());
     return validator.Errors.Union(uniqueness.Errors);
 }
Exemple #6
0
 public IEnumerable<ErrorMessage> Validate(KindDTO kind)
 {
     var kindEntity = kind.To();
     var validator = new ValidateKind(kindEntity.Name, kindEntity.Type);
     var uniqueness = new UniquenessConstraint<Kind>(() => validator.Commit());
     return validator.Errors.Union(uniqueness.Errors);
 }
Exemple #7
0
        /// <summary>
        /// Attempts to fix a PopulationMandatoryError
        /// </summary>
        /// <param name="error">Error to be corrected</param>
        /// <param name="autoCorrectObjectType">The <see cref="ObjectType"/> to correct the error for.</param>
        /// <returns><see langword="true"/> if the error was automatically corrected.</returns>
        public bool AutoCorrectMandatoryError(PopulationMandatoryError error, ObjectType autoCorrectObjectType)
        {
            // Find a role in the mandatory constraint that corresponds to
            // the object type
            Role matchingRole = null;
            UniquenessConstraint           pid      = autoCorrectObjectType.PreferredIdentifier;
            LinkedElementCollection <Role> pidRoles = pid != null ? pid.RoleCollection : null;

            foreach (Role role in error.MandatoryConstraint.RoleCollection)
            {
                SubtypeFact       subtypeFact;
                SupertypeMetaRole supertypeRole;
                if (role.RolePlayer == autoCorrectObjectType ||
                    (null != (supertypeRole = role as SupertypeMetaRole) &&
                     (subtypeFact = (SubtypeFact)supertypeRole.FactType).ProvidesPreferredIdentifier &&
                     subtypeFact.Subtype == autoCorrectObjectType) ||
                    (null != pidRoles && pidRoles.Contains(role)))
                {
                    if (matchingRole != null)
                    {
                        // Multiple matches, nothing to do
                        matchingRole = null;
                        break;
                    }
                    matchingRole = role;
                }
            }
            if (matchingRole != null)
            {
                return(AutoCorrectMandatoryError(error, matchingRole, null));
            }
            return(false);
        }
Exemple #8
0
 private static void SignificantUniquenessConstraintChange(UniquenessConstraint constraint)
 {
     if (constraint != null &&
         !constraint.IsDeleted &&
         !ORMElementGateway.IsElementExcluded(constraint))
     {
         FrameworkDomainModel.DelayValidateElement(constraint, SignificantUniquenessConstraintChangeDelayed);
     }
 }
            /// <summary>
            /// DeleteRule: typeof(UniquenessConstraintIsForUniqueness)
            /// Propagate deletion of a Uniqueness
            /// </summary>
            private static void UniquenessDeletedRule(ElementDeletedEventArgs e)
            {
                UniquenessConstraint constraint = ((UniquenessConstraintIsForUniqueness)e.ModelElement).UniquenessConstraint;

                if (!constraint.IsDeleted)
                {
                    constraint.Delete();
                }
            }
 private void Reset()
 {
     mySelectedRoles          = null;
     mySourceShape            = null;
     myIUC                    = null;
     myLastMouseMoveItem      = null;
     myPendingOnClickedAction = OnClickedAction.Normal;
     FactTypeShape.ActiveInternalUniquenessConstraintConnectAction = null;
 }
        /// <summary>
        /// RolePlayerChangeRule: typeof(ORMSolutions.ORMArchitect.Core.ObjectModel.EntityTypeHasPreferredIdentifier), FireTime=TopLevelCommit, Priority=DiagramFixupConstants.AddShapeRulePriority;
        /// </summary>
        private static void PreferredIdentifierRolePlayerChangeRule(RolePlayerChangedEventArgs e)
        {
            UniquenessConstraint oldPreferredIdentifier = null;

            if (e.DomainRole.Id == EntityTypeHasPreferredIdentifier.PreferredIdentifierDomainRoleId)
            {
                oldPreferredIdentifier = (UniquenessConstraint)e.OldRolePlayer;
            }
            ProcessPreferredIdentifier(e.ElementLink as EntityTypeHasPreferredIdentifier, oldPreferredIdentifier);
        }
 private bool DetermineWhetherFromIsPreferredIdentifier()
 {
     foreach (ConstraintRoleSequence constraintRoleSequence in myFromRole.ConstraintRoleSequenceCollection)
     {
         UniquenessConstraint uniquenessConstraint = constraintRoleSequence as UniquenessConstraint;
         if (uniquenessConstraint != null && uniquenessConstraint.IsPreferred)
         {
             return(true);
         }
     }
     return(false);
 }
Exemple #13
0
        public void UniqueUniqueImplied_1a(Store store)
        {
            myTestServices.LogValidationErrors("Start with one Implication Error");
            ORMModel             model      = store.ElementDirectory.FindElements <ORMModel>()[0];
            UniquenessConstraint constraint = (UniquenessConstraint)model.ConstraintsDictionary.GetElement("ExternalUniquenessConstraint_A").SingleElement;

            myTestServices.LogMessage("Removing the Implied Uniqueness Costraint...");
            using (Transaction t = store.TransactionManager.BeginTransaction("Remove Implied Uniqueness Costraint"))
            {
                constraint.Delete();
                t.Commit();
            }
            myTestServices.LogValidationErrors("Error is removed with removal of Implied Constraint");
        }
 /// <summary>
 /// Helper function for preferred identifier validation
 /// </summary>
 private static void InvalidateForPreferredIdentifier(UniquenessConstraint constraint)
 {
     if (!constraint.IsInternal &&
         !constraint.IsDeleted)
     {
         foreach (PresentationElement pel in PresentationViewsSubject.GetPresentation(constraint))
         {
             ExternalConstraintShape constraintShape = pel as ExternalConstraintShape;
             if (constraintShape != null)
             {
                 constraintShape.Invalidate(true);
             }
         }
     }
 }
Exemple #15
0
			private static void SignificantUniquenessConstraintChange(UniquenessConstraint constraint)
			{
				if (constraint != null &&
					!constraint.IsDeleted &&
					!ORMElementGateway.IsElementExcluded(constraint))
				{
					FrameworkDomainModel.DelayValidateElement(constraint, SignificantUniquenessConstraintChangeDelayed);
				}
			}
            /// <summary>
            /// Binarizes the unary <see cref="FactType"/> specified by <paramref name="unaryFactType"/>, defaulting
            /// to using open-world assumption. The caller is responsible for making sure <paramref name="unaryFactType"/>
            /// is in fact a unary fact type.
            /// </summary>
            public static void BinarizeUnary(FactType unaryFactType, INotifyElementAdded notifyAdded)
            {
                Partition partition = unaryFactType.Partition;
                Store     store     = partition.Store;
                IHasAlternateOwner <FactType>      toAlternateOwner;
                IAlternateElementOwner <FactType>  alternateFactTypeOwner = (null == (toAlternateOwner = unaryFactType as IHasAlternateOwner <FactType>)) ? null : toAlternateOwner.AlternateOwner;
                LinkedElementCollection <RoleBase> roleCollection         = unaryFactType.RoleCollection;

                Debug.Assert(roleCollection.Count == 1, "Unaries should only have one role.");

                Role   unaryRole = (Role)roleCollection[0];
                string implicitBooleanValueTypeName = GetImplicitBooleanValueTypeName(unaryRole);

                // UNDONE: We are using open-world assumption now
                // Setup the mandatory constraint (for closed-world assumption)
                //MandatoryConstraint mandatoryConstraint = MandatoryConstraint.CreateSimpleMandatoryConstraint(unaryRole);
                //mandatoryConstraint.Model = unaryFactType.Model;
                //if (notifyAdded != null)
                //{
                //    notifyAdded.ElementAdded(mandatoryConstraint, true);
                //}

                // Setup the uniqueness constraint (to make the newly binarized FactType valid)
                if (unaryRole.SingleRoleAlethicUniquenessConstraint == null)
                {
                    UniquenessConstraint uniquenessConstraint = UniquenessConstraint.CreateInternalUniquenessConstraint(unaryFactType);
                    uniquenessConstraint.RoleCollection.Add(unaryRole);
                    if (notifyAdded != null)
                    {
                        notifyAdded.ElementAdded(uniquenessConstraint, true);
                    }
                }

                // Setup the boolean role (to make the FactType a binary)
                Role implicitBooleanRole = new Role(partition, null);

                implicitBooleanRole.Name = unaryRole.Name;

                // Setup the boolean value type (because the boolean role needs a role player)

                IAlternateElementOwner <ObjectType> alternateObjectTypeOwner = null;
                DomainClassInfo alternateCtor =
                    (null != alternateFactTypeOwner &&
                     null != (alternateObjectTypeOwner = alternateFactTypeOwner as IAlternateElementOwner <ObjectType>)) ?
                    alternateObjectTypeOwner.GetOwnedElementClassInfo(typeof(ObjectType)) :
                    null;
                PropertyAssignment implicitBooleanProperty  = new PropertyAssignment(ObjectType.IsImplicitBooleanValueDomainPropertyId, true);
                ObjectType         implicitBooleanValueType = (alternateCtor != null) ?
                                                              (ObjectType)partition.ElementFactory.CreateElement(alternateCtor, implicitBooleanProperty) :
                                                              new ObjectType(partition, implicitBooleanProperty);
                Dictionary <object, object> contextInfo = store.TransactionManager.CurrentTransaction.TopLevelTransaction.Context.ContextInfo;
                object duplicateNamesKey         = ORMModel.AllowDuplicateNamesKey;
                bool   removeDuplicateNamesKey   = false;
                object duplicateSignaturesKey    = ORMModel.BlockDuplicateReadingSignaturesKey;
                bool   addDuplicateSignaturesKey = false;

                try
                {
                    if (!contextInfo.ContainsKey(duplicateNamesKey))
                    {
                        contextInfo[duplicateNamesKey] = null;
                        removeDuplicateNamesKey        = true;
                    }
                    if (contextInfo.ContainsKey(duplicateSignaturesKey))
                    {
                        contextInfo[duplicateSignaturesKey] = null;
                        addDuplicateSignaturesKey           = true;
                    }
                    implicitBooleanValueType.Name = implicitBooleanValueTypeName;
                    if (alternateCtor != null)
                    {
                        ((IHasAlternateOwner <ObjectType>)implicitBooleanValueType).AlternateOwner = alternateObjectTypeOwner;
                    }
                    else
                    {
                        implicitBooleanValueType.Model = unaryFactType.ResolvedModel;
                    }
                    if (notifyAdded != null)
                    {
                        notifyAdded.ElementAdded(implicitBooleanValueType, true);
                    }
                }
                finally
                {
                    if (removeDuplicateNamesKey)
                    {
                        contextInfo.Remove(duplicateNamesKey);
                    }
                    if (addDuplicateSignaturesKey)
                    {
                        contextInfo[duplicateSignaturesKey] = null;
                    }
                }
                implicitBooleanValueType.DataType = store.ElementDirectory.FindElements <TrueOrFalseLogicalDataType>(false)[0];

                // Set value constraint on implicit boolean ValueType for open-world assumption
                ValueTypeValueConstraint implicitBooleanValueConstraint = implicitBooleanValueType.ValueConstraint
                                                                              = new ValueTypeValueConstraint(partition, null);

                // Add the true-only ValueRange to the value constraint for open-world assumption
                implicitBooleanValueConstraint.ValueRangeCollection.Add(new ValueRange(partition,
                                                                                       new PropertyAssignment(ValueRange.MinValueDomainPropertyId, bool.TrueString),
                                                                                       new PropertyAssignment(ValueRange.MaxValueDomainPropertyId, bool.TrueString)));

                // Make the boolean value type the role player for the implicit boolean role
                implicitBooleanRole.RolePlayer = implicitBooleanValueType;

                // Add the boolean role to the FactType
                roleCollection.Add(implicitBooleanRole);
                if (notifyAdded != null)
                {
                    notifyAdded.ElementAdded(implicitBooleanRole, true);
                }
            }
        /// <summary>
        /// Overrideable shape painting for use after the paint helper is initialized
        /// </summary>
        /// <param name="e">The event arguments</param>
        /// <param name="helper">The initialized pain helper.</param>
        protected virtual void OnPaintShape(DiagramPaintEventArgs e, ref PaintHelper helper)
        {
            IConstraint  constraint = AssociatedConstraint;
            RectangleD   bounds     = AbsoluteBounds;
            RectangleF   boundsF    = RectangleD.ToRectangleF(bounds);
            Graphics     g          = e.Graphics;
            const double cos45      = 0.70710678118654752440084436210485;

            Pen   pen          = helper.Pen;
            Brush brush        = helper.Brush;
            bool  noDeonticDot = false;

            switch (constraint.ConstraintType)
            {
                #region Frequency
            case ConstraintType.Frequency:
            {
                break;
            }

                #endregion
                #region Ring
            case ConstraintType.Ring:
                // Note: goto default here restores the frowny face. However,
                // with the error feedback, we already have UI indicating there
                // is a problem.
                noDeonticDot = true;
                break;

                #endregion
                #region ValueComparison
            case ConstraintType.ValueComparison:
                noDeonticDot = true;
                break;

                #endregion                 // ValueComparison
                #region Equality
            case ConstraintType.Equality:
            {
                double xOffset = bounds.Width * .3;
                float  xLeft   = (float)(bounds.Left + xOffset);
                float  xRight  = (float)(bounds.Right - xOffset);
                double yCenter = bounds.Top + bounds.Height / 2;
                double yOffset = (double)pen.Width * 1.0;
                float  y       = (float)(yCenter - yOffset);
                g.DrawLine(pen, xLeft, y, xRight, y);
                y = (float)(yCenter + yOffset);
                g.DrawLine(pen, xLeft, y, xRight, y);
                break;
            }

                #endregion
                #region Mandatory
            case ConstraintType.DisjunctiveMandatory:
            {
                // Draw the dot
                RectangleF shrinkBounds = boundsF;
                shrinkBounds.Inflate(-boundsF.Width * .22f, -boundsF.Height * .22f);
                g.FillEllipse(brush, shrinkBounds);
                if (null != ExclusiveOrConstraintCoupler.GetExclusiveOrExclusionConstraint((MandatoryConstraint)constraint))
                {
                    goto case ConstraintType.Exclusion;
                }
                break;
            }

                #endregion
                #region Exclusion
            case ConstraintType.Exclusion:
            {
                // Draw the X
                double offset  = (bounds.Width + pen.Width) * (1 - cos45) / 2;
                float  leftX   = (float)(bounds.Left + offset);
                float  rightX  = (float)(bounds.Right - offset);
                float  topY    = (float)(bounds.Top + offset);
                float  bottomY = (float)(bounds.Bottom - offset);
                g.DrawLine(pen, leftX, topY, rightX, bottomY);
                g.DrawLine(pen, leftX, bottomY, rightX, topY);
                break;
            }

                #endregion
                #region Uniqueness
            case ConstraintType.ExternalUniqueness:
            {
                // Draw a single line for a uniqueness constraint and a double
                // line for preferred uniqueness
                UniquenessConstraint euc = constraint as UniquenessConstraint;
                double widthAdjust       = (double)pen.Width / 2;
                float  xLeft             = (float)(bounds.Left + widthAdjust);
                float  xRight            = (float)(bounds.Right - widthAdjust);
                if (euc.IsPreferred)
                {
                    double yCenter = bounds.Top + bounds.Height / 2;
                    double yOffset = (double)pen.Width * .7;
                    float  y       = (float)(yCenter - yOffset);
                    g.DrawLine(pen, xLeft, y, xRight, y);
                    y = (float)(yCenter + yOffset);
                    g.DrawLine(pen, xLeft, y, xRight, y);
                }
                else
                {
                    float y = (float)(bounds.Top + bounds.Height / 2);
                    g.DrawLine(pen, xLeft, y, xRight, y);
                }
                break;
            }

                #endregion
                #region Subset
            case ConstraintType.Subset:
            {
                RectangleD arcBounds = bounds;
                double     shrinkBy  = -bounds.Height * .35;
                double     yOffset   = pen.Width * .7;
                double     xOffset   = shrinkBy * .35;
                arcBounds.Inflate(shrinkBy, shrinkBy);
                arcBounds.Offset(xOffset, -yOffset);
                g.DrawArc(pen, RectangleD.ToRectangleF(arcBounds), 90, 180);
                float xLeft  = (float)arcBounds.Center.X;
                float xRight = (float)(bounds.Right + shrinkBy - xOffset);
                float y      = (float)arcBounds.Top;
                g.DrawLine(pen, xLeft, y, xRight, y);
                y = (float)arcBounds.Bottom;
                g.DrawLine(pen, xLeft, y, xRight, y);
                y = (float)(arcBounds.Bottom + yOffset + yOffset);
                g.DrawLine(pen, (float)arcBounds.Left, y, xRight, y);
                break;
            }

                #endregion
                #region Fallback (default)
            default:
            {
                // Draws a frowny face
                float  eyeY          = boundsF.Y + (boundsF.Height / 3);
                PointF leftEyeStart  = new PointF(boundsF.X + (boundsF.Width * 0.3f), eyeY);
                PointF leftEyeEnd    = new PointF(boundsF.X + (boundsF.Width * 0.4f), eyeY);
                PointF rightEyeStart = new PointF(boundsF.X + (boundsF.Width * 0.6f), eyeY);
                PointF rightEyeEnd   = new PointF(boundsF.X + (boundsF.Width * 0.7f), eyeY);
                g.DrawLine(pen, leftEyeStart, leftEyeEnd);
                g.DrawLine(pen, rightEyeStart, rightEyeEnd);

                float      mouthLeft      = boundsF.X + (boundsF.Width * 0.25f);
                float      mouthTop       = boundsF.Y + (boundsF.Height * 0.55f);
                RectangleF mouthRectangle = new RectangleF(mouthLeft, mouthTop, boundsF.Width * 0.5f, boundsF.Height * 0.25f);
                g.DrawArc(pen, mouthRectangle, 180, 180);

                break;
            }
                #endregion
            }
            if (!noDeonticDot && constraint.Modality == ConstraintModality.Deontic)
            {
                float startPenWidth = pen.Width;
                pen.Width = startPenWidth * .70f;
                float boxSide = (float)((1 - cos45) * bounds.Width);
                g.FillEllipse(this.StyleSet.GetBrush(DiagramBrushes.DiagramBackground), (float)bounds.Left, (float)bounds.Top, boxSide, boxSide);
                g.DrawArc(pen, (float)bounds.Left, (float)bounds.Top, boxSide, boxSide, 0, 360);
                pen.Width = startPenWidth;
            }
        }
            /// <summary>
            /// Reverses the binarization process performed by <see cref="BinarizeUnary"/>. Typically used when
            /// <paramref name="binarizedUnaryFactRoleCollection"/> no longer qualifies as the roles for a
            /// binarized unary <see cref="FactType"/>.
            /// </summary>
            private static void DebinarizeUnary(LinkedElementCollection <RoleBase> binarizedUnaryFactRoleCollection, bool deleteImplicitBooleanRole, INotifyElementAdded notifyAdded)
            {
                // UNDONE: We need to make sure the debinarization happens BEFORE the implied Objectification rules run on the binarized unary FactType.

                // The default implied role is the second one, walk the collection backwards
                int roleCount = binarizedUnaryFactRoleCollection.Count;

                for (int i = roleCount - 1; i >= 0; --i)
                {
                    Role       implicitBooleanRole;
                    ObjectType implicitBooleanValueType;
                    if (null != (implicitBooleanRole = binarizedUnaryFactRoleCollection[i].Role) &&
                        null != (implicitBooleanValueType = implicitBooleanRole.RolePlayer) &&
                        implicitBooleanValueType.IsImplicitBooleanValue)
                    {
                        // Delete the implicit boolean value type (which will also remove any value constraints on it)
                        // Note that changes to IsImplicitBooleanValue are intentionally blocked so that the
                        // deleted implied ValueType can be identified as such by events as well as rules.
                        // implicitBooleanValueType.IsImplicitBooleanValue = false;
                        bool        ruleDisabled = false;
                        RuleManager ruleManager  = null;
                        try
                        {
                            if (notifyAdded == null)
                            {
                                ruleManager = implicitBooleanRole.Store.RuleManager;
                                ruleManager.DisableRule(typeof(ObjectTypePlaysRoleDeletedRuleClass));
                                ruleDisabled = true;
                            }
                            if (deleteImplicitBooleanRole)
                            {
                                // We delete the role first so that rules do not
                                // try to recreate and implied fact type for this rule
                                // if it is part of an objectified FactType.
                                implicitBooleanRole.Delete();
                                --roleCount;
                                if (!implicitBooleanValueType.IsDeleted)
                                {
                                    // The Objectification.RolePlayerDeletingRule rule will delet this automatically
                                    implicitBooleanValueType.Delete();
                                }
                            }
                            else
                            {
                                implicitBooleanValueType.Delete();
                            }
                        }
                        finally
                        {
                            if (ruleDisabled)
                            {
                                ruleManager.EnableRule(typeof(ObjectTypePlaysRoleDeletedRuleClass));
                            }
                        }

                        // Clear implied constraints
                        for (int j = 0; j < roleCount; ++j)
                        {
                            Role role = binarizedUnaryFactRoleCollection[j] as Role;
                            if (role != null)
                            {
                                if (role != implicitBooleanRole)
                                {
                                    role.Name = "";
                                    // Role cardinality is for unary fact types only, eliminate
                                    // it if we switch away.
                                    role.Cardinality = null;
                                }

                                UniquenessConstraint singleRoleAlethicUniquenessConstraint = role.SingleRoleAlethicUniquenessConstraint;
                                if (singleRoleAlethicUniquenessConstraint != null)
                                {
                                    // Delete the uniqueness constraint
                                    singleRoleAlethicUniquenessConstraint.Delete();
                                }

                                // UNDONE: We are using open-world assumption now
                                //MandatoryConstraint simpleMandatoryConstraint = role.SimpleMandatoryConstraint;
                                //if (simpleMandatoryConstraint != null && simpleMandatoryConstraint.Modality == ConstraintModality.Alethic)
                                //{
                                //    // Delete the simple mandatory constraint (for closed-world assumption), if present
                                //    simpleMandatoryConstraint.Delete();
                                //}
                            }
                        }
                        break;
                    }
                }
            }
 /// <summary>
 /// Rule helper method
 /// </summary>
 private static void ProcessPreferredIdentifier(EntityTypeHasPreferredIdentifier link, UniquenessConstraint preferredIdentifier)
 {
     if (preferredIdentifier == null)
     {
         preferredIdentifier = link.PreferredIdentifier;
     }
     if (!preferredIdentifier.IsDeleted)
     {
         if (preferredIdentifier.IsInternal)
         {
             LinkedElementCollection <FactType> factTypes = preferredIdentifier.FactTypeCollection;
             if (factTypes.Count == 1)
             {
                 FactType        factType = factTypes[0];
                 Objectification objectification;
                 InvalidateAssociatedDisplay(factType);
                 if (null != (objectification = factType.Objectification))
                 {
                     foreach (FactType linkFactType in objectification.ImpliedFactTypeCollection)
                     {
                         InvalidateAssociatedDisplay(linkFactType);
                     }
                 }
             }
         }
         else
         {
             InvalidateAssociatedDisplay(preferredIdentifier);
         }
     }
 }
		/// <summary>
		/// Add a source shape or commit/cancel the action by forwarding the
		/// click to the base class, or modify the current role sequence by handling
		/// the click locally.
		/// </summary>
		/// <param name="e">MouseActionEventArgs</param>
		protected override void OnClicked(MouseActionEventArgs e)
		{
			switch (myPendingOnClickedAction)
			{
				case OnClickedAction.Commit:
					myPendingOnClickedAction = OnClickedAction.Normal;
					// Letting the click through to the base ConnectAction
					// at this point (a constraint is selected and a role has been
					// double-clicked) will force the connect action to finish.
					base.OnClicked(e);
					return;
				case OnClickedAction.CheckForCommit:
					myPendingOnClickedAction = OnClickedAction.Normal;
					break;
			}
			DiagramMouseEventArgs args = CurrentDiagramArgs as DiagramMouseEventArgs;
			if (args != null)
			{
				DiagramItem item = args.DiagramHitTestInfo.HitDiagramItem;
				ModelElement currentElement = null;
				foreach (ModelElement elem in item.RepresentedElements)
				{
					currentElement = elem;
					break;
				}
				UniquenessConstraint internalUniquenessConstraint;
				RoleBase roleBase;
				if (null != (internalUniquenessConstraint = currentElement as UniquenessConstraint) &&
					internalUniquenessConstraint.IsInternal)
				{
					if (mySourceShape == null)
					{
						// Let the click through to the base to officially begin the drag action
						base.OnClicked(e);
						mySourceShape = item.Shape as FactTypeShape;
						myIUC = internalUniquenessConstraint;
					}
				}
				else if (mySourceShape != null)
				{
					if (null != (roleBase = currentElement as RoleBase))
					{
						Role role = roleBase.Role;
						if (role.FactType == mySourceShape.AssociatedFactType)
						{
							// Add or remove the role
							IList<Role> roles = SelectedRoleCollection;
							int roleIndex = roles.IndexOf(role);
							bool forceRedraw = false;
							if (roleIndex >= 0)
							{
								// Only remove a role when the control key is down. Otherwise,
								// there is no way to double-click on a previously selected
								// role without turning it off, and this is a natural gesture.
								// Add shift key as well for discoverability.
								if (0 != (0xff00 & GetKeyState(Keys.ControlKey)) ||
									0 != (0xff00 & GetKeyState(Keys.ShiftKey)))
								{
									forceRedraw = true;
									roles.RemoveAt(roleIndex);
								}
							}
							else
							{
								forceRedraw = true;
								roles.Add(role);
							}
							if (mySourceShape != null)
							{
								myPendingOnClickedAction = OnClickedAction.CheckForCommit;
							}

							if (forceRedraw)
							{
								// Force the shape to redraw
								Debug.Assert(mySourceShape != null); //source shape should have been set
								mySourceShape.Invalidate(true);
							}
						}
					}
					else if (currentElement is ORMDiagram)
					{
						base.OnClicked(e); // Let through to allow a cancel
					}
				}
			}
		}
Exemple #21
0
            private static void EnsureSingleColumnUniqueAndMandatory(SubtypeFact subtypeFact, Role role, bool requireMandatory, INotifyElementAdded notifyAdded)
            {
                LinkedElementCollection <ConstraintRoleSequence> sequences = role.ConstraintRoleSequenceCollection;
                int           sequenceCount  = sequences.Count;
                bool          haveUniqueness = false;
                bool          haveMandatory  = !requireMandatory;
                SetConstraint ic;

                for (int i = sequenceCount - 1; i >= 0; --i)
                {
                    ic = sequences[i] as SetConstraint;
                    if (ic != null && ic.Constraint.ConstraintIsInternal)
                    {
                        if (ic.RoleCollection.Count == 1 && ic.Modality == ConstraintModality.Alethic)
                        {
                            switch (ic.Constraint.ConstraintType)
                            {
                            case ConstraintType.InternalUniqueness:
                                if (haveUniqueness)
                                {
                                    ic.Delete();
                                }
                                else
                                {
                                    haveUniqueness = true;
                                }
                                break;

                            case ConstraintType.SimpleMandatory:
                                if (haveMandatory)
                                {
                                    ic.Delete();
                                }
                                else
                                {
                                    haveMandatory = true;
                                }
                                break;
                            }
                        }
                        else
                        {
                            ic.Delete();
                        }
                    }
                }
                if (!haveUniqueness || !haveMandatory)
                {
                    IHasAlternateOwner <FactType>          toAlternateOwner;
                    IAlternateElementOwner <SetConstraint> alternateConstraintOwner;
                    if (null != (toAlternateOwner = subtypeFact as IHasAlternateOwner <FactType>) &&
                        null != (alternateConstraintOwner = toAlternateOwner.AlternateOwner as IAlternateElementOwner <SetConstraint>))
                    {
                        if (!haveUniqueness)
                        {
                            ic = UniquenessConstraint.CreateInternalUniquenessConstraint(subtypeFact);
                            ic.RoleCollection.Add(role);
                            notifyAdded.ElementAdded(ic, true);
                        }
                    }
                    if (!haveMandatory)
                    {
                        ic = MandatoryConstraint.CreateSimpleMandatoryConstraint(role);
                        notifyAdded.ElementAdded(ic, true);
                    }
                }
            }
        /// <summary>See <see cref="ORMShapeToolboxHelperBase.CreateElementToolPrototype"/>.</summary>
        protected sealed override ElementGroupPrototype CreateElementToolPrototype(Store store, Guid domainClassId)
        {
            // WARNING: This method is _extremely_ order-sensitive. If the order that the toolbox items are listed
            // in the .dsl file changes, or if the DSL Tools text template that is used to generate ORMShapeModelToolboxHelperBase
            // changes, this method will most likely need to be changed as well.

            ElementGroup group       = null;
            bool         unknownItem = false;

            if (domainClassId.Equals(ObjectType.DomainClassId))
            {
                group = new ElementGroup(store);
                ObjectType objectType = new ObjectType(store);
                group.AddGraph(objectType, true);
                switch (myObjectTypeCount++)
                {
                case 0:
                    // EntityType - We don't need to do anything else...
                    break;

                case 1:
                    // ValueType
                    // Do not try to set the IsValueType property here. IsValueType picks
                    // up the default data type for the model, which can only be done
                    // when the model is known. Instead, flag the element so that it
                    // can be set during MergeRelate on the model.
                    group.UserData = ORMModel.ValueTypeUserDataKey;
                    break;

                case 2:
                    // ObjectifiedFactType
                    group.AddGraph(new Objectification(objectType, AddFactType(store, group, 2)), false);
                    break;

                default:
                    unknownItem = true;
                    break;
                }
            }
            else if (domainClassId.Equals(FactType.DomainClassId))
            {
                group = new ElementGroup(store);
                Debug.Assert(myFactTypeCount < 3);
                AddFactType(store, group, ++myFactTypeCount);
            }
            else if (domainClassId.Equals(ExclusiveOrConstraintCoupler.DomainClassId))
            {
                group = new ElementGroup(store);
                MandatoryConstraint mandatory = new MandatoryConstraint(store, null);
                group.AddGraph(mandatory, true);
                ExclusionConstraint exclusion = new ExclusionConstraint(store, null);
                group.AddGraph(exclusion, true);
                group.AddGraph(new ExclusiveOrConstraintCoupler(mandatory, exclusion), false);
            }
            else if (domainClassId.Equals(UniquenessConstraint.DomainClassId))
            {
                group = new ElementGroup(store);
                if (myUniquenessConstraintCount == 0)
                {
                    // Add this here so that we can distinguish between internal and external uniqueness
                    // constraints without unpacking the model. We want to merge internals into a fact
                    // and externals into the model.
                    group.UserData = ORMModel.InternalUniquenessConstraintUserDataKey;
                    group.AddGraph(UniquenessConstraint.CreateInternalUniquenessConstraint(store.DefaultPartition), true);
                }
                else
                {
                    Debug.Assert(myUniquenessConstraintCount == 1);
                    group.AddGraph(new UniquenessConstraint(store), true);
                }
                myUniquenessConstraintCount++;
            }
            return((group == null || unknownItem) ? base.CreateElementToolPrototype(store, domainClassId) : group.CreatePrototype());
        }
		private void Reset()
		{
			mySelectedRoles = null;
			mySourceShape = null;
			myIUC = null;
			myLastMouseMoveItem = null;
			myPendingOnClickedAction = OnClickedAction.Normal;
			FactTypeShape.ActiveInternalUniquenessConstraintConnectAction = null;
		}
		/// <summary>
		/// Central function to return member variables to a clean state.
		/// Called by the constructor and the deactivation sequence.
		/// </summary>
		private void Reset()
		{
			myAddedConstraint = null;
			myDropTargetShape = null;
		}
		/// <summary>
		/// Set this mouse action as the active action on the
		/// diagram of the given shape.
		/// </summary>
		/// <param name="attachToShape">The shape the constraint is being attached to.</param>
		/// <param name="constraint">The constraint being connected.</param>
		/// <param name="clientView">The active DiagramClientView</param>
		public void ChainMouseAction(FactTypeShape attachToShape, UniquenessConstraint constraint, DiagramClientView clientView)
		{
			DiagramView activeView = Diagram.ActiveDiagramView;
			if (activeView != null)
			{
				// Move on to the selection action
				clientView.ActiveMouseAction = this;

				// Now emulate a mouse click in the middle of the added constraint. The click
				// actions provide a starting point for the connect action, so a mouse move
				// provides a drag line.
				Point emulateClickPoint = clientView.WorldToDevice(attachToShape.GetAbsoluteConstraintAttachPoint(constraint));
				DiagramMouseEventArgs mouseEventArgs = new DiagramMouseEventArgs(new MouseEventArgs(MouseButtons.Left, 1, emulateClickPoint.X, emulateClickPoint.Y, 0), clientView);
				MouseDown(mouseEventArgs);
				Click(new DiagramPointEventArgs(emulateClickPoint.X, emulateClickPoint.Y, PointRelativeTo.Client, clientView));
				MouseUp(mouseEventArgs);
				attachToShape.Invalidate(true);

				// An extra move lets us chain when the mouse is not on the design surface,
				// such as when we are being activated via the task list.
				MouseMove(mouseEventArgs);

				ORMDiagram.SelectToolboxItem(activeView, ResourceStrings.ToolboxInternalUniquenessConstraintItemId);
				FactTypeShape.ActiveInternalUniquenessConstraintConnectAction = this;
			}
		}
		/// <summary>
		/// Rule helper method
		/// </summary>
		private static void ProcessPreferredIdentifier(EntityTypeHasPreferredIdentifier link, UniquenessConstraint preferredIdentifier)
		{
			if (preferredIdentifier == null)
			{
				preferredIdentifier = link.PreferredIdentifier;
			}
			if (!preferredIdentifier.IsDeleted)
			{
				if (preferredIdentifier.IsInternal)
				{
					LinkedElementCollection<FactType> factTypes = preferredIdentifier.FactTypeCollection;
					if (factTypes.Count == 1)
					{
						FactType factType = factTypes[0];
						Objectification objectification;
						InvalidateAssociatedDisplay(factType);
						if (null != (objectification = factType.Objectification))
						{
							foreach (FactType linkFactType in objectification.ImpliedFactTypeCollection)
							{
								InvalidateAssociatedDisplay(linkFactType);
							}
						}
					}
				}
				else
				{
					InvalidateAssociatedDisplay(preferredIdentifier);
				}
			}
		}
Exemple #27
0
        /// <summary>
        /// Ensure that the <see cref="UniquenessConstraint.IsPreferred"/> property is read-only
        /// when the <see cref="FactType.InternalUniquenessConstraintChangeRule"/> is
        /// unable to make it <see langword="true"/>.
        /// Make sure the <see cref="SetConstraint.Modality">Modality</see> property
        /// is read only for single-role uniqueness constraints on the Objectification end of an implied fact type.
        /// </summary>
        protected override bool IsPropertyDescriptorReadOnly(ElementPropertyDescriptor propertyDescriptor)
        {
            UniquenessConstraint uniquenessConstraint;
            Guid propertyId = propertyDescriptor.DomainPropertyInfo.Id;
            LinkedElementCollection <Role> roles;
            FactType factType;

            if (propertyId == UniquenessConstraint.IsPreferredDomainPropertyId)
            {
                uniquenessConstraint = ModelElement;
                ObjectType identifierFor = uniquenessConstraint.PreferredIdentifierFor;
                if (identifierFor != null)
                {
                    // If this is the preferred identifier for an objectifying type and
                    // is the only alethic internal uniqueness constraint for the nested FactType,
                    // then it will automatically be readded as the preferred identifier if it is
                    // changed to false. Don't allow it to change.
                    if (uniquenessConstraint.IsInternal &&
                        null != (factType = identifierFor.NestedFactType))
                    {
                        UniquenessConstraint           candidate       = null;
                        LinkedElementCollection <Role> constraintRoles = uniquenessConstraint.RoleCollection;
                        if (constraintRoles.Count == 1 && constraintRoles[0] is ObjectifiedUnaryRole)                         // Note there is only one FactType for an internal constraint
                        {
                            candidate = uniquenessConstraint;
                        }
                        else if (factType == uniquenessConstraint.FactTypeCollection[0] && null == factType.UnaryRole)
                        {
                            foreach (UniquenessConstraint constraint in factType.GetInternalConstraints <UniquenessConstraint>())
                            {
                                if (constraint.Modality == ConstraintModality.Alethic)
                                {
                                    if (candidate != null || constraint != uniquenessConstraint)
                                    {
                                        candidate = null;
                                        break;
                                    }
                                    else
                                    {
                                        candidate = constraint;
                                    }
                                }
                            }
                        }
                        if (candidate != null)
                        {
                            bool haveSupertype = false;
                            ObjectType.WalkSupertypeRelationships(
                                identifierFor,
                                delegate(SubtypeFact subtypeFact, ObjectType type, int depth)
                            {
                                // Note that we do not check if the supertype is a preferred
                                // path here, only that supertypes are available.
                                haveSupertype = true;
                                return(ObjectTypeVisitorResult.Stop);
                            });
                            return(!haveSupertype);
                        }
                    }
                    return(false);
                }
                else
                {
                    return(!uniquenessConstraint.TestAllowPreferred(null, false));
                }
            }
            else if (propertyId == UniquenessConstraint.ModalityDomainPropertyId &&
                     (uniquenessConstraint = ModelElement).Store != null &&
                     uniquenessConstraint.IsInternal &&
                     (roles = uniquenessConstraint.RoleCollection).Count == 1 &&
                     ((factType = roles[0].FactType).ImpliedByObjectification != null ||
                      factType is SubtypeFact))
            {
                return(true);
            }
            return(base.IsPropertyDescriptorReadOnly(propertyDescriptor));
        }
		/// <summary>
		/// An IMS event to track the shape element added to the associated
		/// diagram during this connect action.
		/// </summary>
		/// <param name="sender"></param>
		/// <param name="e"></param>
		private void InternalConstraintAddedEvent(object sender, ElementAddedEventArgs e)
		{
			if (myAddedConstraint == null)
			{
				UniquenessConstraint candidate = e.ModelElement as UniquenessConstraint;
				if (candidate != null && candidate.IsInternal)
				{
					ORMDiagram d = Diagram as ORMDiagram;
					if (d != null)
					{
						// Find the shape associated with the fact type we added to
						LinkedElementCollection<FactType> candidateFacts = candidate.FactTypeCollection;
						if (candidateFacts.Count != 0)
						{
							FactTypeShape shape = d.FindShapeForElement(candidateFacts[0]) as FactTypeShape;
							if (shape != null)
							{
								myDropTargetShape = shape;
								myAddedConstraint = candidate;
							}
						}
					}
				}
			}
		}
 /// <summary>
 /// Central function to return member variables to a clean state.
 /// Called by the constructor and the deactivation sequence.
 /// </summary>
 private void Reset()
 {
     myAddedConstraint = null;
     myDropTargetShape = null;
 }
        /// <summary>
        /// Add a source shape or commit/cancel the action by forwarding the
        /// click to the base class, or modify the current role sequence by handling
        /// the click locally.
        /// </summary>
        /// <param name="e">MouseActionEventArgs</param>
        protected override void OnClicked(MouseActionEventArgs e)
        {
            switch (myPendingOnClickedAction)
            {
            case OnClickedAction.Commit:
                myPendingOnClickedAction = OnClickedAction.Normal;
                // Letting the click through to the base ConnectAction
                // at this point (a constraint is selected and a role has been
                // double-clicked) will force the connect action to finish.
                base.OnClicked(e);
                return;

            case OnClickedAction.CheckForCommit:
                myPendingOnClickedAction = OnClickedAction.Normal;
                break;
            }
            DiagramMouseEventArgs args = CurrentDiagramArgs as DiagramMouseEventArgs;

            if (args != null)
            {
                DiagramItem  item           = args.DiagramHitTestInfo.HitDiagramItem;
                ModelElement currentElement = null;
                foreach (ModelElement elem in item.RepresentedElements)
                {
                    currentElement = elem;
                    break;
                }
                UniquenessConstraint internalUniquenessConstraint;
                RoleBase             roleBase;
                if (null != (internalUniquenessConstraint = currentElement as UniquenessConstraint) &&
                    internalUniquenessConstraint.IsInternal)
                {
                    if (mySourceShape == null)
                    {
                        // Let the click through to the base to officially begin the drag action
                        base.OnClicked(e);
                        mySourceShape = item.Shape as FactTypeShape;
                        myIUC         = internalUniquenessConstraint;
                    }
                }
                else if (mySourceShape != null)
                {
                    if (null != (roleBase = currentElement as RoleBase))
                    {
                        Role role = roleBase.Role;
                        if (role.FactType == mySourceShape.AssociatedFactType)
                        {
                            // Add or remove the role
                            IList <Role> roles       = SelectedRoleCollection;
                            int          roleIndex   = roles.IndexOf(role);
                            bool         forceRedraw = false;
                            if (roleIndex >= 0)
                            {
                                // Only remove a role when the control key is down. Otherwise,
                                // there is no way to double-click on a previously selected
                                // role without turning it off, and this is a natural gesture.
                                // Add shift key as well for discoverability.
                                if (0 != (0xff00 & GetKeyState(Keys.ControlKey)) ||
                                    0 != (0xff00 & GetKeyState(Keys.ShiftKey)))
                                {
                                    forceRedraw = true;
                                    roles.RemoveAt(roleIndex);
                                }
                            }
                            else
                            {
                                forceRedraw = true;
                                roles.Add(role);
                            }
                            if (mySourceShape != null)
                            {
                                myPendingOnClickedAction = OnClickedAction.CheckForCommit;
                            }

                            if (forceRedraw)
                            {
                                // Force the shape to redraw
                                Debug.Assert(mySourceShape != null);                                 //source shape should have been set
                                mySourceShape.Invalidate(true);
                            }
                        }
                    }
                    else if (currentElement is ORMDiagram)
                    {
                        base.OnClicked(e);                         // Let through to allow a cancel
                    }
                }
            }
        }
		/// <summary>
		/// Helper function for preferred identifier validation
		/// </summary>
		private static void InvalidateForPreferredIdentifier(UniquenessConstraint constraint)
		{
			if (!constraint.IsInternal &&
				!constraint.IsDeleted)
			{
				foreach (PresentationElement pel in PresentationViewsSubject.GetPresentation(constraint))
				{
					ExternalConstraintShape constraintShape = pel as ExternalConstraintShape;
					if (constraintShape != null)
					{
						constraintShape.Invalidate(true);
					}
				}
			}
		}
Exemple #32
0
		/// <summary>
		/// Get all value roles including all roles directly attached to the provided
		/// object type and any roles descended from this one through prefererred identifiers.
		/// Walks the opposite direction of <see cref="Role.GetValueRoles()"/>
		/// </summary>
		/// <param name="anchorType">The <see cref="ObjectType"/> to walk descended roles for</param>
		/// <param name="unattachedRole">A role to test that is not currently attached to the anchorType.
		/// If unattachedRole is not null, then only this role will be tested. Otherwise, all current played
		/// roles will be walked.</param>
		/// <param name="unattachedPreferredIdentifier">A preferred identifier to test that is not currently
		/// attached to the anchorType.</param>
		/// <param name="visitor">A <see cref="ValueRoleVisitor"/> callback delegate.</param>
		public static void WalkDescendedValueRoles(ObjectType anchorType, Role unattachedRole, UniquenessConstraint unattachedPreferredIdentifier, ValueRoleVisitor visitor)
		{
			ValueTypeHasDataType dataTypeLink = anchorType.GetDataTypeLink();
			if (null == unattachedPreferredIdentifier &&
				null != (dataTypeLink = anchorType.GetDataTypeLink()))
			{
				ObjectType unattachedRolePlayer;
				WalkDescendedValueRoles(
					(unattachedRole != null) ? new Role[] { unattachedRole } as IList<Role> : anchorType.PlayedRoleCollection,
					RolePathObjectTypeRoot.GetLinksToRolePathCollection(anchorType),
					dataTypeLink,
					anchorType.ValueConstraint,
					null,
					(null == unattachedRole || null == (unattachedRolePlayer = unattachedRole.RolePlayer)) ? false : !unattachedRolePlayer.IsValueType,
					visitor);
			}
			else
			{
				LinkedElementCollection<Role> roles;
				UniquenessConstraint preferredIdentifier;
				if (null != (preferredIdentifier = unattachedPreferredIdentifier ?? anchorType.ResolvedPreferredIdentifier) &&
					(roles = preferredIdentifier.RoleCollection).Count == 1)
				{
					Role currentRole = roles[0];
					Role[] valueRoles = currentRole.GetValueRoles();
					if (valueRoles != null)
					{
						ValueConstraint nearestValueConstraint = null;
						int valueRolesCount = valueRoles.Length;
						for (int i = valueRolesCount - 1; i >= 0; --i)
						{
							nearestValueConstraint = valueRoles[i].ValueConstraint;
							if (nearestValueConstraint != null)
							{
								break;
							}
						}
						ObjectType valueType = valueRoles[0].RolePlayer;
						dataTypeLink = valueType.GetDataTypeLink();
						if (nearestValueConstraint == null)
						{
							nearestValueConstraint = valueType.ValueConstraint;
						}
						RoleBase nextSkipRole = currentRole.OppositeRoleAlwaysResolveProxy;
						if (nextSkipRole != null)
						{
							WalkDescendedValueRoles(
								(unattachedRole != null) ? new Role[] { unattachedRole } as IList<Role> : anchorType.PlayedRoleCollection,
								RolePathObjectTypeRoot.GetLinksToRolePathCollection(anchorType),
								dataTypeLink,
								nearestValueConstraint,
								nextSkipRole.Role,
								true,
								visitor);
						}
					}
				}
			}
		}