Code:
/ 4.0 / 4.0 / untmp / DEVDIV_TFS / Dev10 / Releases / RTMRel / ndp / cdf / src / NetFx40 / System.Activities / System / Activities / Statements / Flowchart.cs / 1305376 / Flowchart.cs
//------------------------------------------------------------------------------ // Copyright (c) Microsoft Corporation. All rights reserved. //----------------------------------------------------------------------------- namespace System.Activities.Statements { using System.Activities; using System.Collections.Generic; using System.Collections.ObjectModel; using System.Runtime; using System.Runtime.Collections; using System.Windows.Markup; [ContentProperty("Nodes")] public sealed class Flowchart : NativeActivity { Collectionvariables; Collection nodes; Collection allNodes; CompletionCallback onStepCompleted; CompletionCallback onDecisionCompleted; Variable currentNode; public Flowchart() { this.currentNode = new Variable (); this.allNodes = new Collection (); } public Collection Variables { get { if (this.variables == null) { this.variables = new ValidatingCollection { // disallow null values OnAddValidationCallback = item => { if (item == null) { throw FxTrace.Exception.ArgumentNull("item"); } } }; } return this.variables; } } [DependsOn("Variables")] public FlowNode StartNode { get; set; } [DependsOn("StartNode")] public Collection Nodes { get { if (this.nodes == null) { this.nodes = new ValidatingCollection { // disallow null values OnAddValidationCallback = item => { if (item == null) { throw FxTrace.Exception.ArgumentNull("item"); } } }; } return this.nodes; } } protected override void CacheMetadata(NativeActivityMetadata metadata) { metadata.SetVariablesCollection(this.Variables); metadata.AddImplementationVariable(this.currentNode); GatherAllNodes(metadata); HashSet uniqueChildren = new HashSet (); for (int i = 0; i < this.allNodes.Count; i++) { this.allNodes[i].GetChildActivities(uniqueChildren); } List children = new List (uniqueChildren.Count); foreach (Activity child in uniqueChildren) { children.Add(child); } metadata.SetChildrenCollection(new Collection (children)); } void GatherAllNodes(NativeActivityMetadata metadata) { // Clear out our cached list of all nodes this.allNodes.Clear(); if (this.StartNode == null && this.Nodes.Count > 0) { metadata.AddValidationError(SR.FlowchartMissingStartNode(this.DisplayName)); } else { DepthFirstVisitNodes((n) => VisitNode(n, metadata), this.StartNode); } } // Returns true if we should visit connected nodes bool VisitNode(FlowNode node, NativeActivityMetadata metadata) { if (node.Open(this, metadata)) { Fx.Assert(node.Index == -1 && !this.allNodes.Contains(node), "Corrupt Flowchart.allNodes."); node.Index = this.allNodes.Count; this.allNodes.Add(node); return true; } return false; } void DepthFirstVisitNodes(Func visitNodeCallback, FlowNode start) { Fx.Assert(visitNodeCallback != null, "This must be supplied since it stops us from infinitely looping."); List connected = new List (); Stack stack = new Stack (); if (start == null) { return; } stack.Push(start); while (stack.Count > 0) { FlowNode current = stack.Pop(); if (current == null) { continue; } if (visitNodeCallback(current)) { connected.Clear(); current.GetConnectedNodes(connected); for (int i = 0; i < connected.Count; i++) { stack.Push(connected[i]); } } } } protected override void Execute(NativeActivityContext context) { if (this.StartNode != null) { if (TD.FlowchartStartIsEnabled()) { TD.FlowchartStart(this.DisplayName); } ExecuteNodeChain(context, this.StartNode, null); } else { if (TD.FlowchartEmptyIsEnabled()) { TD.FlowchartEmpty(this.DisplayName); } } } void ExecuteNodeChain(NativeActivityContext context, FlowNode node, ActivityInstance completedInstance) { if (node == null) { if (context.IsCancellationRequested) { Fx.Assert(completedInstance != null, "cannot request cancel if we never scheduled any children"); // we are done but the last child didn't complete successfully if (completedInstance.State != ActivityInstanceState.Closed) { context.MarkCanceled(); } } return; } if (context.IsCancellationRequested) { // we're not done and cancel has been requested context.MarkCanceled(); return; } Fx.Assert(node != null, "caller should validate"); FlowNode current = node; do { FlowNode next; if (ExecuteSingleNode(context, current, out next)) { current = next; } else { this.currentNode.Set(context, current.Index); current = null; } } while (current != null); } bool ExecuteSingleNode(NativeActivityContext context, FlowNode node, out FlowNode nextNode) { Fx.Assert(node != null, "caller should validate"); FlowStep step = node as FlowStep; if (step != null) { if (this.onStepCompleted == null) { this.onStepCompleted = new CompletionCallback(OnStepCompleted); } return step.Execute(context, this.onStepCompleted, out nextNode); } nextNode = null; FlowDecision decision = node as FlowDecision; if (decision != null) { if (this.onDecisionCompleted == null) { this.onDecisionCompleted = new CompletionCallback (OnDecisionCompleted); } return decision.Execute(context, this.onDecisionCompleted); } IFlowSwitch switchNode = node as IFlowSwitch; Fx.Assert(switchNode != null, "unrecognized FlowNode"); return switchNode.Execute(context, this); } FlowNode GetCurrentNode(NativeActivityContext context) { int index = this.currentNode.Get(context); FlowNode result = this.allNodes[index]; Fx.Assert(result != null, "corrupt internal state"); return result; } void OnStepCompleted(NativeActivityContext context, ActivityInstance completedInstance) { FlowStep step = GetCurrentNode(context) as FlowStep; Fx.Assert(step != null, "corrupt internal state"); FlowNode next = step.Next; ExecuteNodeChain(context, next, completedInstance); } void OnDecisionCompleted(NativeActivityContext context, ActivityInstance completedInstance, bool result) { FlowDecision decision = GetCurrentNode(context) as FlowDecision; Fx.Assert(decision != null, "corrupt internal state"); FlowNode next = result ? decision.True : decision.False; ExecuteNodeChain(context, next, completedInstance); } internal void OnSwitchCompleted (NativeActivityContext context, ActivityInstance completedInstance, T result) { IFlowSwitch switchNode = GetCurrentNode(context) as IFlowSwitch; Fx.Assert(switchNode != null, "corrupt internal state"); FlowNode next = switchNode.GetNextNode(result); ExecuteNodeChain(context, next, completedInstance); } } } // File provided for Reference Use Only by Microsoft Corporation (c) 2007.
Link Menu
This book is available now!
Buy at Amazon US or
Buy at Amazon UK
- QuerySelectOp.cs
- ReflectPropertyDescriptor.cs
- TypeNameConverter.cs
- NativeRightsManagementAPIsStructures.cs
- SafeViewOfFileHandle.cs
- PngBitmapDecoder.cs
- FixedSOMTableRow.cs
- LineInfo.cs
- DriveNotFoundException.cs
- ServiceModelPerformanceCounters.cs
- ZipIOExtraFieldPaddingElement.cs
- CaseStatementProjectedSlot.cs
- FileAuthorizationModule.cs
- FileIOPermission.cs
- Brush.cs
- SetMemberBinder.cs
- PagePropertiesChangingEventArgs.cs
- TagMapInfo.cs
- IntegerValidatorAttribute.cs
- FixedHyperLink.cs
- DataSourceXmlAttributeAttribute.cs
- Rights.cs
- ProxyElement.cs
- XPathNavigatorReader.cs
- SqlReferenceCollection.cs
- LongCountAggregationOperator.cs
- XmlSchemaComplexContentRestriction.cs
- SimpleWorkerRequest.cs
- TextChangedEventArgs.cs
- SqlPersistenceProviderFactory.cs
- DataGridView.cs
- TraceUtility.cs
- ArrangedElement.cs
- DocumentReferenceCollection.cs
- LocalValueEnumerator.cs
- LayoutEngine.cs
- SelectionChangedEventArgs.cs
- ToolStripOverflowButton.cs
- VariableAction.cs
- ProcessProtocolHandler.cs
- CssTextWriter.cs
- AsymmetricSignatureDeformatter.cs
- RegisteredHiddenField.cs
- SequenceRangeCollection.cs
- PtsPage.cs
- RowBinding.cs
- CapabilitiesSection.cs
- ManagementExtension.cs
- CompiledQueryCacheEntry.cs
- PageBorderless.cs
- TypeForwardedToAttribute.cs
- XPathParser.cs
- DayRenderEvent.cs
- WinFormsUtils.cs
- MemberExpression.cs
- BuildManagerHost.cs
- UnsafeNativeMethods.cs
- EntityClassGenerator.cs
- RootBrowserWindowProxy.cs
- DelegatedStream.cs
- CacheSection.cs
- CodeDomConfigurationHandler.cs
- QilPatternVisitor.cs
- XmlSchemaValidationException.cs
- PatternMatcher.cs
- XmlDictionary.cs
- ResourceDictionary.cs
- PathGeometry.cs
- WindowsRichEditRange.cs
- StrokeIntersection.cs
- Win32Exception.cs
- Stroke2.cs
- Region.cs
- BooleanFacetDescriptionElement.cs
- querybuilder.cs
- AssemblyBuilderData.cs
- SystemTcpStatistics.cs
- EdmItemCollection.cs
- BypassElementCollection.cs
- RelatedImageListAttribute.cs
- CancelEventArgs.cs
- SettingsAttributes.cs
- ModelFunction.cs
- OutputCacheSettings.cs
- ResourceContainer.cs
- VirtualDirectoryMapping.cs
- UpdateCommandGenerator.cs
- SessionPageStatePersister.cs
- FontEditor.cs
- GeneralTransform3DGroup.cs
- RequestCache.cs
- CodeIterationStatement.cs
- Socket.cs
- DatatypeImplementation.cs
- EntityConnectionStringBuilder.cs
- XmlnsCompatibleWithAttribute.cs
- TimelineCollection.cs
- RegexFCD.cs
- ServicePointManagerElement.cs
- DataDocumentXPathNavigator.cs