<?xml version="1.0" encoding="utf-8"?>
<rss xmlns:atom="http://www.w3.org/2005/Atom" xmlns:sy="http://purl.org/rss/1.0/modules/syndication/" xmlns:dc="http://purl.org/dc/elements/1.1/" xmlns:content="http://purl.org/rss/1.0/modules/content/" xmlns:wfw="http://wellformedweb.org/CommentAPI/" xmlns:slash="http://purl.org/rss/1.0/modules/slash/"
  version="2.0">
  <channel>
    <title>Go with the Flow</title>
    <atom:link
      href="https://docs.microsoft.com/archive/blogs/flow/feed.xml"
      rel="self"
      type="application/rss+xml" />
    <link>https://docs.microsoft.com/archive/blogs/flow/feed.xml</link>
    <description />
    <lastBuildDate>Wed, 17 Apr 2019 03:23:06 GMT</lastBuildDate>
    <language>en-US</language>
    <sy:updatePeriod>hourly</sy:updatePeriod>
    <sy:updateFrequency>1</sy:updateFrequency>
    <item>
      <title>[How To] Save WF4 Workflow Definition to Image Using Code</title>
      <link>https://docs.microsoft.com/archive/blogs/flow/how-to-save-wf4-workflow-definition-to-image-using-code</link>
      <pubDate>Tue, 16 Aug 2011 02:48:24 GMT</pubDate>
      <dc:creator><![CDATA[Guang Yang - MSFT]]></dc:creator>
      <guid
        isPermaLink="false">https://blogs.msdn.microsoft.com/flow/2011/08/16/how-to-save-wf4-workflow-definition-to-image-using-code/</guid>
      <description><![CDATA[One of the benefits of using WF4 to create workflow is that it provides a graphical workflow...]]></description>
      <content:encoded><![CDATA[<p><font size="2">One of the benefits of using WF4 to create workflow is that it provides a graphical workflow designer. This means in most of the cases, developers don’t need to write code to define their workflows. Instead, they can use the graphical workflow designer we provided. This can not only dramatically improve the productivity but also bring down the barrier of authoring workflows so that even non-developers can do so. Another advantage of this kind of graphical design is that it’s intuitive and easy to understand. This is why it’s been used so far in almost all kinds of workflow solutions.</font></p>  <p><font size="2">In some scenarios, you may want to save your workflow definitions to images so that you can use them later. For example:</font></p>  <ol>   <li><font size="2">Attach them in some document</font> </li>    <li><font size="2">Show them in some web pages to illustrate the definitions of the workflows</font> </li>    <li><font size="2">Etc.</font> </li> </ol>  <p><font size="2">You may have already noticed that you can save the workflow definition to an image by <strong>right click</strong> on the designer surface and like <strong>Copy as Image</strong> or <strong>Save as Image</strong>. However, this is a manual approach. <strong>What if I want to write some code to save the images?</strong> You may ask.</font></p>  <p><font size="2"><strong>Good news is, you can do it. Bad news is, you need to write some code, maybe a little bit more than you expected. (If you don’t want read the entire blog, you can find the sample I used <a href="https://msdnshared.blob.core.windows.net/media/MSDNBlogsFS/prod.evol.blogs.msdn.com/CommunityServer.Blogs.Components.WeblogFiles/00/00/01/32/28/code/8372.SaveImage.zip" original-url="http://blogs.msdn.com/cfs-file.ashx/__key/CommunityServer-Blogs-Components-WeblogFiles/00-00-01-32-28-code/8372.SaveImage.zip">here</a>)</strong></font></p>  <p><font size="2">“What the hack?” You may wonder. Shouldn’t there be a public API for me to use? Even WF 3.x has that API. Well, it appears to be it should till you get to know why we didn’t provide one. But hanging there. It’s not hard to implement it by yourself. I promise. It will also help you to have a better understanding about how workflow designer works.</font></p>  <h1><font size="2">Why there is no public API for this?</font></h1>  <p><font size="2">WF4 workflow designer is written in WPF while WF 3.x workflow designer is written in WinForm. This is a very significant difference. WPF doesn’t support generating an image of the UI when the UI itself has been drawn yet. So <strong>in order to save a workflow definition to an image, you need to create and actually make WPF draw the workflow definition in a workflow designer first</strong>.</font></p>  <p><font size="2">This is the main reason why we didn’t provide any public API for saving as image. Because even if we did, you will only be able to use it after the workflow designer is opened, which is confusing. And it’s hard to imagine Microsoft will release an API in .NET Framework saying “You have to call it after you open the workflow designer UI”. That’s just bad API.</font></p>  <h1><font size="2">Basic idea of the solution</font></h1>  <p><font size="2">OK, knowing why we didn’t provide a public API for this. Let’s look at how we are going to achieve the goal by ourselves. At the high level, we need to</font></p>  <ol>   <li><font size="2">Create a workflow designer </font></li>    <li><font size="2">Load the workflow definition which you want to save to an image </font></li>    <li><font size="2">Make sure the workflow designer is drawn by WPF (basically putting it into a visible UI control) </font></li>    <li><font size="2">Capture an image of the workflow definition </font></li>    <li><font size="2">Save the image to a file </font></li>    <li><font size="2">Close the workflow designer </font></li> </ol>  <p><font size="2">For the sake of convenience, I won’t show you how to create a rehost workflow designer. Instead, I’ll jump in directly to the “save image” part. You can find a sample of creating rehost workflow designer </font><a href="http://msdn.microsoft.com/en-us/library/dd699776.aspx"><font size="2">here</font></a><font size="2">.</font></p>  <h1><font size="2">Let’s try some code</font></h1>  <p><font size="2">OK, let’s write some code. Following is a code snippet showing the basic idea of a rehost workflow designer.</font></p>  <pre class="code"><font size="2"><font face="Consolas"><span style="color: blue">namespace </span>Microsoft.Samples.DesignerRehosting
{
    <span style="color: blue">public partial class </span><span style="color: #2b91af">RehostingWfDesigner </span>: </font></font><font size="2"><font face="Consolas"><span style="color: #2b91af">Window
    </span>{
        <span style="color: blue">private </span><span style="color: #2b91af">WorkflowDesigner </span>workflowDesigner;

        <span style="color: blue">public </span>RehostingWfDesigner()
        {
            InitializeComponent();
        }

        <span style="color: blue">protected override void </span>OnInitialized(<span style="color: #2b91af">EventArgs </span>e)
        {
            <span style="color: blue">base</span>.OnInitialized(e);

            </font></font><font size="2"><font face="Consolas"><span style="color: green">// register metadata
            </span>(<span style="color: blue">new </span><span style="color: #2b91af">DesignerMetadata</span>()).Register();
            </font></font><font size="2"><font face="Consolas"><span style="color: green">// create a big workflow for saving image
            </span><span style="color: #2b91af">Activity </span>workflow = <span style="color: blue">new </span></font></font><font size="2"><font face="Consolas"><span style="color: #2b91af">Sequence
            </span>{
                Activities = { 
                    <span style="color: blue">new </span><span style="color: #2b91af">Sequence</span>(), <span style="color: blue">new </span><span style="color: #2b91af">Sequence</span>(), <span style="color: blue">new </span><span style="color: #2b91af">Sequence</span>(),
                    <span style="color: blue">new </span><span style="color: #2b91af">Sequence</span>(), <span style="color: blue">new </span><span style="color: #2b91af">Sequence</span>(), <span style="color: blue">new </span><span style="color: #2b91af">Sequence</span>(),
                    <span style="color: blue">new </span><span style="color: #2b91af">Sequence</span>(), <span style="color: blue">new </span><span style="color: #2b91af">Sequence</span>(), <span style="color: blue">new </span><span style="color: #2b91af">Sequence</span>()
                }
            };
            </font></font><font size="2"><font face="Consolas"><span style="color: green">// create the workflow designer and load the workflow
            </span>workflowDesigner = <span style="color: blue">new </span><span style="color: #2b91af">WorkflowDesigner</span>();
            workflowDesigner.Load(workflow);
            DesignerBorder.Child = workflowDesigner.View;
        }
    }
}</font></font></pre>


<p><font size="2">Now let’s look at how to generate an image of the workflow definition using the standard mechanism of WPF. After all, workflow designer canvas is a WPF control.</font></p>

<pre class="code"><font face="Consolas"><font size="2"><span style="color: #2b91af">BitmapFrame </span>CreateWorkflowDefinitionImage()
{
    <span style="color: blue">const double </span>DPI = 96.0;
    </font></font><font face="Consolas"><font size="2"><span style="color: green">// this is the designer area we want to save
    </span><span style="color: #2b91af">Visual </span>areaToSave = ((<span style="color: #2b91af">DesignerView</span>)<span style="color: #2b91af">VisualTreeHelper</span>.GetChild(
        <span style="color: blue">this</span>.workflowDesigner.View, 0)).RootDesigner;
    </font></font><font face="Consolas"><font size="2"><span style="color: green">// get the size of the targeting area
    </span><span style="color: #2b91af">Rect </span>size = <span style="color: #2b91af">VisualTreeHelper</span>.GetDescendantBounds(areaToSave);
    <span style="color: #2b91af">RenderTargetBitmap </span>bitmap = <span style="color: blue">new </span><span style="color: #2b91af">RenderTargetBitmap</span>((<span style="color: blue">int</span>)size.Width, (<span style="color: blue">int</span>)size.Height,
       DPI, DPI, <span style="color: #2b91af">PixelFormats</span>.Pbgra32);
    bitmap.Render(areaToSave);
    <span style="color: blue">return </span><span style="color: #2b91af">BitmapFrame</span>.Create(bitmap);
}</font></font></pre>


<p><font size="2">The above C# method is very straightforward. Just get the workflow diagram part of the workflow designer and create an in-memory image of it using some WPF API. The next thing is simple: create a file and save the image.</font></p>

<pre class="code"><font face="Consolas"><font size="2"><span style="color: blue">void </span>SaveImageToFile(<span style="color: blue">string </span>fileName, <span style="color: #2b91af">BitmapFrame </span>image)
{
    <span style="color: blue">using </span>(<span style="color: #2b91af">FileStream </span>fs = <span style="color: blue">new </span><span style="color: #2b91af">FileStream</span>(fileName, <span style="color: #2b91af">FileMode</span>.Create))
    {
        <span style="color: #2b91af">BitmapEncoder </span>encoder = <span style="color: blue">new </span><span style="color: #2b91af">JpegBitmapEncoder</span>();
        encoder.Frames.Add(<span style="color: #2b91af">BitmapFrame</span>.Create(image));
        encoder.Save(fs);
        fs.Close();
    }
}</font></font></pre>


<div class="csharpcode">
  <pre><span class="lnum"></span></pre>
</div>


<p><font size="2">At last, let’s try to invoke the above 2 methods in the <strong>OnInitialized()</strong> method to hook it up and then close the application.</font></p>

<pre class="code"><font face="Consolas"><font size="2"><span style="color: blue">protected override void </span>OnInitialized(<span style="color: #2b91af">EventArgs </span>e)
{
</font></font><font face="Consolas"><font size="2"><span style="color: green">    // ...
    </span><span style="color: blue">this</span>.SaveImageToFile(<span style="color: #a31515">&quot;test.jpg&quot;</span>, <span style="color: blue">this</span>.CreateWorkflowDefinitionImage());
    <span style="color: #2b91af">Application</span>.Current.Shutdown();
}</font></font></pre>


<h1><font size="2">Exception? What the hell?</font></h1>

<p><font size="2">Run the code to have a try. Wait a sec, exception thrown. What?</font></p>

<p><font size="2"><a href="https://msdnshared.blob.core.windows.net/media/MSDNBlogsFS/prod.evol.blogs.msdn.com/CommunityServer.Blogs.Components.WeblogFiles/00/00/01/32/28/metablogapi/5367.exception_18B27E8C.png" original-url="http://blogs.msdn.com/cfs-file.ashx/__key/CommunityServer-Blogs-Components-WeblogFiles/00-00-01-32-28-metablogapi/5367.exception_5F00_18B27E8C.png"><img style="display: inline" src="https://msdnshared.blob.core.windows.net/media/MSDNBlogsFS/prod.evol.blogs.msdn.com/CommunityServer.Blogs.Components.WeblogFiles/00/00/01/32/28/metablogapi/5367.exception_18B27E8C.png" original-url="http://blogs.msdn.com/cfs-file.ashx/__key/CommunityServer-Blogs-Components-WeblogFiles/00-00-01-32-28-metablogapi/5367.exception_5F00_18B27E8C.png" width="406" height="248" /></a></font></p>

<p><font size="2">After some debugging work, it’s not hard to find that <strong>the root cause of this exception is because the size of the UI control we are trying to capture is negative</strong>. </font></p>

<p><font size="2">Why? This is because although we invoked the above 2 methods to save the image after creating the workflow designer, the workflow designer hasn’t been fully created by WPF yet.</font></p>

<p><font size="2">You may know that every WPF UI control has a <strong>LayoutUpdated</strong> event, meaning the layout has been completed. This sounds like a plan. However, only this is not enough, ‘cause before workflow designer draws the workflow definition completely, the layout will be changed multiple times, which will trigger multiple LayoutUpdated events. In order to solve this issue, <strong>we need a Timer</strong>.</font></p>

<pre class="code"><font face="Consolas"><font size="2"><span style="color: blue">private </span><span style="color: #2b91af">Timer </span>timer;
<span style="color: blue">private delegate void </span><span style="color: #2b91af">TimerDelegate</span>();

<span style="color: blue">protected override void </span>OnInitialized(<span style="color: #2b91af">EventArgs </span>e)
{
    <span style="color: blue">this</span>.timer = <span style="color: blue">new </span>System.Timers.<span style="color: #2b91af">Timer</span>(1000);
    <span style="color: blue">this</span>.timer.AutoReset = <span style="color: blue">false</span>;
    <span style="color: blue">this</span>.timer.Elapsed += <span style="color: blue">new </span><span style="color: #2b91af">ElapsedEventHandler</span>(CaptureTimer_Elapsed);
    <span style="color: blue">this</span>.timer.Start();
    workflowDesigner.View.LayoutUpdated += <span style="color: blue">new </span><span style="color: #2b91af">EventHandler</span>(View_LayoutUpdated);
}

<span style="color: blue">void </span>CaptureTimer_Elapsed(<span style="color: blue">object </span>sender, <span style="color: #2b91af">ElapsedEventArgs </span>e)
{
    <span style="color: blue">this</span>.timer.Stop();
    <span style="color: blue">this</span>.timer = <span style="color: blue">null</span>;
    <span style="color: blue">this</span>.workflowDesigner.View.Dispatcher.BeginInvoke(
        System.Windows.Threading.<span style="color: #2b91af">DispatcherPriority</span>.ApplicationIdle,
        (<span style="color: #2b91af">TimerDelegate</span>)<span style="color: blue">delegate</span>()
        {
            <span style="color: blue">this</span>.SaveImageToFile(<span style="color: #a31515">&quot;test.jpg&quot;</span>, <span style="color: blue">this</span>.CreateWorkflowDefinitionImage());
            <span style="color: #2b91af">Application</span>.Current.Shutdown();
        });
}

<span style="color: blue">void </span>View_LayoutUpdated(<span style="color: blue">object </span>sender, <span style="color: #2b91af">EventArgs </span>e)
{
    <span style="color: blue">if </span>(<span style="color: blue">this</span>.timer != <span style="color: blue">null</span>)
    {
        <span style="color: blue">this</span>.timer.Stop();
        <span style="color: blue">this</span>.timer.Start();
    }
}</font></font></pre>


<p><font size="2">Now let’s try it again. Good! No exceptions any more! Check out the bin\Debug folder. Bam, there it is, test.jpg.</font></p>

<p><font size="2"></font></p>

<h1><font size="2">No exception, good. But wait, why I get a uncompleted image?</font></h1>

<p><font size="2">Now you may think it’s done, which unfortunately is not the case. Open the image and take a look. You will find that the there will be several Sequence activities at the bottom shown as blank box. Why did this happen? (The image should be vertical. I rotated the image here in order to save some space.)</font></p>

<p><a href="https://msdnshared.blob.core.windows.net/media/MSDNBlogsFS/prod.evol.blogs.msdn.com/CommunityServer.Blogs.Components.WeblogFiles/00/00/01/32/28/metablogapi/8345.test_6E8ACE72.jpg" original-url="http://blogs.msdn.com/cfs-filesystemfile.ashx/__key/communityserver-blogs-components-weblogfiles/00-00-01-32-28-metablogapi/8345.test_5F00_6E8ACE72.jpg"><img src="https://msdnshared.blob.core.windows.net/media/MSDNBlogsFS/prod.evol.blogs.msdn.com/CommunityServer.Blogs.Components.WeblogFiles/00/00/01/32/28/metablogapi/8345.test_6E8ACE72.jpg" original-url="http://blogs.msdn.com/cfs-filesystemfile.ashx/__key/communityserver-blogs-components-weblogfiles/00-00-01-32-28-metablogapi/8345.test_5F00_6E8ACE72.jpg" /></a></p>

<p><font size="2">In order to understand this, we need to discuss a advanced mechanism of workflow designer: <strong>Virtualization</strong>. Imagine you have a huge workflow. When you open it in workflow designer, since the viewport is a fixed size (based on the size of your workflow designer window), it’s a big waste to draw all parts of the workflow since only a small portion will be shown at once. So what virtualization does is delay the drawing of the workflow diagram till when you really need it, which means when you move the viewport to the specific region. This can improve the performance of workflow designer dramatically.</font></p>

<p><font size="2">However, it also causes some trouble when you are trying to save an image. Because <strong>due to virtualization when you invoke the methods to save the image, the workflow diagram hasn’t been drawn completely yet</strong>.</font></p>

<h1><font size="2">Filling the last piece</font></h1>

<p><font size="2">So how can we solve this problem? Well, you may notice that there is a <strong>Fit to Screen</strong> button in workflow designer. <strong>The only we need to do is to use this button to show the entire workflow before capturing the image</strong>. See the following code.</font></p>

<pre class="code"><font face="Consolas"><font size="2"><span style="color: blue">private bool </span>IsVirtualized = <span style="color: blue">false</span>;

<span style="color: blue">void </span>View_LayoutUpdated(<span style="color: blue">object </span>sender, <span style="color: #2b91af">EventArgs </span>e)
{
    <span style="color: blue">if </span>(!IsVirtualized)
    {
        ((<span style="color: #2b91af">RoutedCommand</span>)<span style="color: #2b91af">DesignerView</span>.FitToScreenCommand).Execute(<span style="color: blue">null</span>,
            <span style="color: blue">this</span>.workflowDesigner.Context.Services.GetService&lt;<span style="color: #2b91af">DesignerView</span>&gt;());
        IsVirtualized = <span style="color: blue">true</span>;
    }
    <span style="color: blue">if </span>(<span style="color: blue">this</span>.timer != <span style="color: blue">null</span>)
    {
        <span style="color: blue">this</span>.timer.Stop();
        <span style="color: blue">this</span>.timer.Start();
    }
}</font></font></pre>


<p><font size="2">Now let’s run the project for one last time. Bingo! All the activities have been captured successfully!</font></p>

<h1><font size="2">Conclusion</font></h1>

<p><font size="2">I hope this is not too overwhelming to you. Although the code I showed above is not the most intuitive one, but I hope you can understand why we need to write it in this way. Again, we would love to provide a kick-ass API but there are constraints.</font></p>

<p><font size="2">You can find the full sample code <a href="https://msdnshared.blob.core.windows.net/media/MSDNBlogsFS/prod.evol.blogs.msdn.com/CommunityServer.Blogs.Components.WeblogFiles/00/00/01/32/28/code/8372.SaveImage.zip" original-url="http://blogs.msdn.com/cfs-file.ashx/__key/CommunityServer-Blogs-Components-WeblogFiles/00-00-01-32-28-code/8372.SaveImage.zip">here</a>. Hope this would help and let me know if you have any questions/feedbacks.</font></p>]]></content:encoded>
    </item>
    <item>
      <title>Hotfix from WPF to Solve Workflow Designer Hang Issue in Some Cases</title>
      <link>https://docs.microsoft.com/archive/blogs/flow/hotfix-from-wpf-to-solve-workflow-designer-hang-issue-in-some-cases</link>
      <pubDate>Tue, 09 Aug 2011 19:22:00 GMT</pubDate>
      <dc:creator><![CDATA[Guang Yang - MSFT]]></dc:creator>
      <guid
        isPermaLink="false">https://blogs.msdn.microsoft.com/flow/2011/08/09/hotfix-from-wpf-to-solve-workflow-designer-hang-issue-in-some-cases/</guid>
      <description><![CDATA[Recently we've received a few customer feedbacks reporting WF4 workflow designer would have bad...]]></description>
      <content:encoded><![CDATA[<p>Recently we've received a few customer feedbacks reporting WF4 workflow designer would have bad performance or hang in some cases even when the workflow is relatively small. We've worked with customers and found out that it was actually a WPF issue.</p>
<p>Good news is, the WPF team has already release a hotfix for it. So if you are experiencing bad performance/hang with WF4 workflow designer, I would recommend you to install this hotfix and try again. Although I cannot guarantee it will solve the issue in your case (since the root cause may be different), there is still a good chance that it will help.</p>
<p>You can find the hotfix using either of the links below.</p>
<p><a href="http://archive.msdn.microsoft.com/KB2484841" title="http://archive.msdn.microsoft.com/KB2484841">http://archive.msdn.microsoft.com/KB2484841</a></p>
<p><a href="http://connect.microsoft.com/VisualStudio/Downloads/DownloadDetails.aspx?DownloadID=35604" title="http://archive.msdn.microsoft.com/KB2484841">http://connect.microsoft.com/VisualStudio/Downloads/DownloadDetails.aspx?DownloadID=35604</a></p>
<p><a href="http://connect.microsoft.com/VisualStudio/Downloads/DownloadDetails.aspx?DownloadID=35604" title="http://archive.msdn.microsoft.com/KB2484841"></a>I would also encourage you to download the following .NET cumulative update patch which includes a bunch of other improvements from WPF and WF4 workflow designer.</p>
<p><a href="http://www.microsoft.com/download/en/details.aspx?id=3556" title="http://www.microsoft.com/download/en/details.aspx?id=3556">http://www.microsoft.com/download/en/details.aspx?id=3556</a></p>
<p>Have a try and tell us whether it works for you~</p>]]></content:encoded>
    </item>
    <item>
      <title>Workflow Foundation 4.0 Activity Data Model (III)</title>
      <link>https://docs.microsoft.com/archive/blogs/flow/workflow-foundation-4-0-activity-data-model-iii</link>
      <pubDate>Tue, 27 Apr 2010 15:56:00 GMT</pubDate>
      <dc:creator><![CDATA[Yun Jin]]></dc:creator>
      <guid
        isPermaLink="false">https://blogs.msdn.microsoft.com/flow/2010/04/27/workflow-foundation-4-0-activity-data-model-iii/</guid>
      <description><![CDATA[We talked about WF4 Activity overview and WF parameters in particular in previous posts. In this...]]></description>
      <content:encoded><![CDATA[<P>We talked about <A title="Workflow Activity Data Model" href="http://blogs.msdn.com/flow/archive/2010/04/05/workflow-foundation-4-0-activity-data-model-i.aspx" mce_href="http://blogs.msdn.com/flow/archive/2010/04/05/workflow-foundation-4-0-activity-data-model-i.aspx">WF4 Activity overview</A> and <A title="Workflow Activity Argument" href="http://blogs.msdn.com/flow/archive/2010/04/06/workflow-foundation-4-0-activity-data-model-ii.aspx" mce_href="http://blogs.msdn.com/flow/archive/2010/04/06/workflow-foundation-4-0-activity-data-model-ii.aspx">WF parameters in particular</A> in previous posts. In this installment, I'm going to focus on WF variables.</P>
<H1 style="MARGIN: 24pt 0in 0pt"><FONT size=5><FONT color=#365f91><FONT face=Cambria>Variable<?xml:namespace prefix = o ns = "urn:schemas-microsoft-com:office:office" /><o:p></o:p></FONT></FONT></FONT></H1>
<P style="MARGIN: 0in 0in 10pt" class=MsoNormal><FONT size=3><FONT face=Calibri>Variables are modeled by Variable class.<o:p></o:p></FONT></FONT></P>
<P style="LINE-HEIGHT: normal; MARGIN: 0in 0in 0pt; mso-layout-grid-align: none" class=MsoNormal><SPAN style="FONT-FAMILY: NSimSun; COLOR: blue; FONT-SIZE: 9pt; mso-bidi-font-family: NSimSun"><SPAN style="mso-spacerun: yes">&nbsp;&nbsp;&nbsp; </SPAN>namespace</SPAN><SPAN style="FONT-FAMILY: NSimSun; FONT-SIZE: 9pt; mso-bidi-font-family: NSimSun"> System.Activities<o:p></o:p></SPAN></P>
<P style="LINE-HEIGHT: normal; MARGIN: 0in 0in 0pt; mso-layout-grid-align: none" class=MsoNormal><SPAN style="FONT-FAMILY: NSimSun; FONT-SIZE: 9pt; mso-bidi-font-family: NSimSun"><SPAN style="mso-spacerun: yes">&nbsp;&nbsp;&nbsp; </SPAN>{<SPAN style="COLOR: blue"><SPAN style="mso-spacerun: yes">&nbsp;&nbsp; </SPAN><o:p></o:p></SPAN></SPAN></P>
<P style="LINE-HEIGHT: normal; MARGIN: 0in 0in 0pt; mso-layout-grid-align: none" class=MsoNormal><SPAN style="FONT-FAMILY: NSimSun; COLOR: blue; FONT-SIZE: 9pt; mso-bidi-font-family: NSimSun"><SPAN style="mso-spacerun: yes">&nbsp;&nbsp;&nbsp; </SPAN><SPAN style="mso-spacerun: yes">&nbsp;&nbsp;&nbsp;&nbsp;</SPAN>public</SPAN><SPAN style="FONT-FAMILY: NSimSun; FONT-SIZE: 9pt; mso-bidi-font-family: NSimSun"> <SPAN style="COLOR: blue">abstract</SPAN> <SPAN style="COLOR: blue">class</SPAN> <SPAN style="COLOR: #2b91af">Variable</SPAN> : <SPAN style="COLOR: #2b91af">LocationReference</SPAN><o:p></o:p></SPAN></P>
<P style="LINE-HEIGHT: normal; MARGIN: 0in 0in 0pt; mso-layout-grid-align: none" class=MsoNormal><SPAN style="FONT-FAMILY: NSimSun; FONT-SIZE: 9pt; mso-bidi-font-family: NSimSun"><SPAN style="mso-spacerun: yes">&nbsp;&nbsp;&nbsp; </SPAN><SPAN style="mso-spacerun: yes">&nbsp;&nbsp;&nbsp;&nbsp;</SPAN>{<o:p></o:p></SPAN></P>
<P style="LINE-HEIGHT: normal; MARGIN: 0in 0in 0pt; mso-layout-grid-align: none" class=MsoNormal><SPAN style="FONT-FAMILY: NSimSun; FONT-SIZE: 9pt; mso-bidi-font-family: NSimSun"><SPAN style="mso-spacerun: yes">&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp; </SPAN><SPAN style="mso-spacerun: yes">&nbsp;&nbsp;&nbsp;&nbsp;</SPAN><SPAN style="COLOR: blue">public</SPAN> <SPAN style="COLOR: #2b91af">ActivityWithResult</SPAN> Default { <SPAN style="COLOR: blue">get</SPAN>; <SPAN style="COLOR: blue">set</SPAN>; }<o:p></o:p></SPAN></P>
<P style="LINE-HEIGHT: normal; MARGIN: 0in 0in 0pt; mso-layout-grid-align: none" class=MsoNormal><SPAN style="FONT-FAMILY: NSimSun; FONT-SIZE: 9pt; mso-bidi-font-family: NSimSun"><SPAN style="mso-spacerun: yes">&nbsp;&nbsp;&nbsp; </SPAN><SPAN style="mso-spacerun: yes">&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;</SPAN><SPAN style="COLOR: blue">public</SPAN> <SPAN style="COLOR: blue">string</SPAN> Name { <SPAN style="COLOR: blue">get</SPAN>; <SPAN style="COLOR: blue">set</SPAN>; }<o:p></o:p></SPAN></P>
<P style="LINE-HEIGHT: normal; MARGIN: 0in 0in 0pt; mso-layout-grid-align: none" class=MsoNormal><SPAN style="FONT-FAMILY: NSimSun; FONT-SIZE: 9pt; mso-bidi-font-family: NSimSun"><SPAN style="mso-spacerun: yes">&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp; </SPAN><SPAN style="mso-spacerun: yes">&nbsp;&nbsp;&nbsp;&nbsp;</SPAN>…<o:p></o:p></SPAN></P>
<P style="LINE-HEIGHT: normal; MARGIN: 0in 0in 0pt; mso-layout-grid-align: none" class=MsoNormal><SPAN style="FONT-FAMILY: NSimSun; FONT-SIZE: 9pt; mso-bidi-font-family: NSimSun"><SPAN style="mso-spacerun: yes">&nbsp;&nbsp;&nbsp; </SPAN><SPAN style="mso-spacerun: yes">&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;</SPAN><SPAN style="COLOR: blue">public</SPAN> <SPAN style="COLOR: blue">object</SPAN> Get(<SPAN style="COLOR: #2b91af">ActivityContext</SPAN> context);<SPAN style="mso-spacerun: yes">&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp; </SPAN><SPAN style="COLOR: blue"><o:p></o:p></SPAN></SPAN></P>
<P style="LINE-HEIGHT: normal; MARGIN: 0in 0in 0pt; mso-layout-grid-align: none" class=MsoNormal><SPAN style="FONT-FAMILY: NSimSun; COLOR: blue; FONT-SIZE: 9pt; mso-bidi-font-family: NSimSun"><SPAN style="mso-spacerun: yes">&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp; </SPAN>public</SPAN><SPAN style="FONT-FAMILY: NSimSun; FONT-SIZE: 9pt; mso-bidi-font-family: NSimSun"> <SPAN style="COLOR: blue">void</SPAN> Set(<SPAN style="COLOR: #2b91af">ActivityContext</SPAN> context, <SPAN style="COLOR: blue">object</SPAN> value);<o:p></o:p></SPAN></P>
<P style="LINE-HEIGHT: normal; MARGIN: 0in 0in 0pt; mso-layout-grid-align: none" class=MsoNormal><SPAN style="FONT-FAMILY: NSimSun; FONT-SIZE: 9pt; mso-bidi-font-family: NSimSun"><SPAN style="mso-spacerun: yes">&nbsp;&nbsp;&nbsp; </SPAN><SPAN style="mso-spacerun: yes">&nbsp;&nbsp;&nbsp;&nbsp;</SPAN>}<o:p></o:p></SPAN></P>
<P style="TEXT-INDENT: 0.25in; MARGIN: 0in 0in 10pt" class=MsoNormal><SPAN style="LINE-HEIGHT: 115%; FONT-FAMILY: NSimSun; FONT-SIZE: 9pt; mso-bidi-font-family: NSimSun">}<o:p></o:p></SPAN></P>
<P style="LINE-HEIGHT: normal; MARGIN: 0in 0in 0pt; mso-layout-grid-align: none" class=MsoNormal><SPAN style="FONT-FAMILY: NSimSun; COLOR: blue; FONT-SIZE: 9pt; mso-bidi-font-family: NSimSun"><SPAN style="mso-spacerun: yes">&nbsp;&nbsp;&nbsp; </SPAN>public</SPAN><SPAN style="FONT-FAMILY: NSimSun; FONT-SIZE: 9pt; mso-bidi-font-family: NSimSun"> <SPAN style="COLOR: blue">sealed</SPAN> <SPAN style="COLOR: blue">class</SPAN> <SPAN style="COLOR: #2b91af">Variable</SPAN>&lt;T&gt; : <SPAN style="COLOR: #2b91af">Variable</SPAN><o:p></o:p></SPAN></P>
<P style="LINE-HEIGHT: normal; MARGIN: 0in 0in 0pt; mso-layout-grid-align: none" class=MsoNormal><SPAN style="FONT-FAMILY: NSimSun; FONT-SIZE: 9pt; mso-bidi-font-family: NSimSun"><SPAN style="mso-spacerun: yes">&nbsp;&nbsp;&nbsp; </SPAN>{<o:p></o:p></SPAN></P>
<P style="LINE-HEIGHT: normal; MARGIN: 0in 0in 0pt; mso-layout-grid-align: none" class=MsoNormal><SPAN style="FONT-FAMILY: NSimSun; FONT-SIZE: 9pt; mso-bidi-font-family: NSimSun"><SPAN style="mso-spacerun: yes">&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp; </SPAN><SPAN style="COLOR: blue">public</SPAN> <SPAN style="COLOR: #2b91af">Activity</SPAN>&lt;T&gt; Default { <SPAN style="COLOR: blue">get</SPAN>; <SPAN style="COLOR: blue">set</SPAN>; }<o:p></o:p></SPAN></P>
<P style="LINE-HEIGHT: normal; MARGIN: 0in 0in 0pt; mso-layout-grid-align: none" class=MsoNormal><SPAN style="FONT-FAMILY: NSimSun; FONT-SIZE: 9pt; mso-bidi-font-family: NSimSun"><SPAN style="mso-spacerun: yes">&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp; </SPAN>…<o:p></o:p></SPAN></P>
<P style="LINE-HEIGHT: normal; MARGIN: 0in 0in 0pt; mso-layout-grid-align: none" class=MsoNormal><SPAN style="FONT-FAMILY: NSimSun; FONT-SIZE: 9pt; mso-bidi-font-family: NSimSun"><SPAN style="mso-spacerun: yes">&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp; </SPAN><SPAN style="COLOR: blue">public</SPAN> T Get(<SPAN style="COLOR: #2b91af">ActivityContext</SPAN> context);<o:p></o:p></SPAN></P>
<P style="LINE-HEIGHT: normal; MARGIN: 0in 0in 0pt; mso-layout-grid-align: none" class=MsoNormal><SPAN style="FONT-FAMILY: NSimSun; FONT-SIZE: 9pt; mso-bidi-font-family: NSimSun"><SPAN style="mso-spacerun: yes">&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp; </SPAN><SPAN style="COLOR: blue">public</SPAN> <SPAN style="COLOR: blue">void</SPAN> Set(<SPAN style="COLOR: #2b91af">ActivityContext</SPAN> context, T value);<o:p></o:p></SPAN></P>
<P style="LINE-HEIGHT: normal; MARGIN: 0in 0in 0pt; mso-layout-grid-align: none" class=MsoNormal><SPAN style="FONT-FAMILY: NSimSun; FONT-SIZE: 9pt; mso-bidi-font-family: NSimSun"><SPAN style="mso-spacerun: yes">&nbsp;&nbsp;&nbsp; </SPAN>}<o:p></o:p></SPAN></P>
<P style="TEXT-INDENT: 0.25in; MARGIN: 0in 0in 10pt" class=MsoNormal><SPAN style="LINE-HEIGHT: 115%; FONT-FAMILY: NSimSun; FONT-SIZE: 9pt; mso-bidi-font-family: NSimSun"><o:p>&nbsp;</o:p></SPAN></P>
<P style="MARGIN: 0in 0in 10pt" class=MsoCaption><STRONG><FONT color=#4f81bd><FONT face=Calibri><SPAN style="mso-spacerun: yes">&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp; </SPAN>Code <SPAN style="mso-no-proof: yes">15</SPAN>. Variable class definition<o:p></o:p></FONT></FONT></STRONG></P>
<P style="MARGIN: 0in 0in 10pt" class=MsoNormal><FONT size=3><FONT face=Calibri>The most basic attributes of a variable should be name and type. Name is defined as a property in Variable abstract class; type is captured by generic type argument of Variable&lt;T&gt;, concrete subclass of Variable. Similar to Argument, Variable also has Get()method to get runtime value from ActivityContext, and Set() method for the other way around.<o:p></o:p></FONT></FONT></P>
<H2 style="MARGIN: auto 0in"><SPAN style="FONT-FAMILY: 'Cambria','serif'; COLOR: #365f91; FONT-SIZE: 12pt; mso-fareast-font-family: 宋体; mso-bidi-font-family: 'Times New Roman'; mso-ascii-theme-font: major-latin; mso-hansi-theme-font: major-latin; mso-fareast-theme-font: major-fareast; mso-bidi-theme-font: major-bidi; mso-themecolor: accent1; mso-themeshade: 191">Public and Implementation Variable<o:p></o:p></SPAN></H2>
<P style="MARGIN: 0in 0in 10pt" class=MsoNormal><FONT size=3><FONT face=Calibri>So far we could always map WF4’s data model back to similar concept of typical procedural language like C#. There is one exception though when it comes to variables.<o:p></o:p></FONT></FONT></P>
<P style="MARGIN: 0in 0in 10pt" class=MsoNormal><FONT size=3><FONT face=Calibri>In C#, variables are used to share data among statements within a scope (e.g, a method). Those statements are considered private to that scope, so are the variable. It’s natural to think an Activity is a method in WF, and its child Activities as statements of the method. Along this line of thinking, any variable should also be private to its defining Activity and accessible by all child Activities. <o:p></o:p></FONT></FONT></P>
<P style="MARGIN: 0in 0in 10pt" class=MsoNormal><FONT size=3><FONT face=Calibri>But in WF, a lot of Activities are to model control flows and their child Activities are actually given by users of those Activities. For example, Sequence is used to execute a list of child Activities, but those child Activities are not defined by Sequence itself, but injected from outside. The closest concept in C# for this is delegate, so let me try to simulate Sequence Activity with a C# method using delegate:<o:p></o:p></FONT></FONT></P>
<P style="LINE-HEIGHT: normal; MARGIN: 0in 0in 0pt; mso-layout-grid-align: none" class=MsoNormal><SPAN style="FONT-FAMILY: NSimSun; COLOR: blue; FONT-SIZE: 9.5pt; mso-bidi-font-family: NSimSun"><SPAN style="mso-spacerun: yes">&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp; </SPAN>static</SPAN><SPAN style="FONT-FAMILY: NSimSun; FONT-SIZE: 9.5pt; mso-bidi-font-family: NSimSun"> <SPAN style="COLOR: blue">void</SPAN> Sequence(<SPAN style="COLOR: blue">params</SPAN> <SPAN style="COLOR: #2b91af">Action</SPAN>[] statements)<o:p></o:p></SPAN></P>
<P style="LINE-HEIGHT: normal; MARGIN: 0in 0in 0pt; mso-layout-grid-align: none" class=MsoNormal><SPAN style="FONT-FAMILY: NSimSun; FONT-SIZE: 9.5pt; mso-bidi-font-family: NSimSun"><SPAN style="mso-spacerun: yes">&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp; </SPAN>{<o:p></o:p></SPAN></P>
<P style="LINE-HEIGHT: normal; MARGIN: 0in 0in 0pt; mso-layout-grid-align: none" class=MsoNormal><SPAN style="FONT-FAMILY: NSimSun; FONT-SIZE: 9.5pt; mso-bidi-font-family: NSimSun"><SPAN style="mso-spacerun: yes">&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp; </SPAN><SPAN style="COLOR: blue">foreach</SPAN> (<SPAN style="COLOR: #2b91af">Action</SPAN> statement <SPAN style="COLOR: blue">in</SPAN> statements)<o:p></o:p></SPAN></P>
<P style="LINE-HEIGHT: normal; MARGIN: 0in 0in 0pt; mso-layout-grid-align: none" class=MsoNormal><SPAN style="FONT-FAMILY: NSimSun; FONT-SIZE: 9.5pt; mso-bidi-font-family: NSimSun"><SPAN style="mso-spacerun: yes">&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp; </SPAN>{<o:p></o:p></SPAN></P>
<P style="LINE-HEIGHT: normal; MARGIN: 0in 0in 0pt; mso-layout-grid-align: none" class=MsoNormal><SPAN style="FONT-FAMILY: NSimSun; FONT-SIZE: 9.5pt; mso-bidi-font-family: NSimSun"><SPAN style="mso-spacerun: yes">&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp; </SPAN>statement();<o:p></o:p></SPAN></P>
<P style="LINE-HEIGHT: normal; MARGIN: 0in 0in 0pt; mso-layout-grid-align: none" class=MsoNormal><SPAN style="FONT-FAMILY: NSimSun; FONT-SIZE: 9.5pt; mso-bidi-font-family: NSimSun"><SPAN style="mso-spacerun: yes">&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp; </SPAN>}<o:p></o:p></SPAN></P>
<P style="LINE-HEIGHT: normal; MARGIN: 0in 0in 0pt; mso-layout-grid-align: none" class=MsoNormal><SPAN style="FONT-FAMILY: NSimSun; FONT-SIZE: 9.5pt; mso-bidi-font-family: NSimSun"><SPAN style="mso-spacerun: yes">&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp; </SPAN>}<o:p></o:p></SPAN></P>
<P style="MARGIN: 0in 0in 10pt" class=MsoCaption><STRONG><FONT color=#4f81bd><FONT face=Calibri><SPAN style="mso-spacerun: yes">&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp; </SPAN>Code <SPAN style="mso-no-proof: yes">16. simulate Sequence Activity using a C# method</SPAN></FONT></FONT></STRONG></P>
<P style="MARGIN: 0in 0in 10pt" class=MsoNormal><FONT size=3><FONT face=Calibri>One would call Sequence method like this:<o:p></o:p></FONT></FONT></P>
<P style="LINE-HEIGHT: normal; MARGIN: 0in 0in 0pt; mso-layout-grid-align: none" class=MsoNormal><SPAN style="FONT-FAMILY: NSimSun; FONT-SIZE: 9.5pt; mso-bidi-font-family: NSimSun"><SPAN style="mso-spacerun: yes">&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp; </SPAN>Sequence(<o:p></o:p></SPAN></P>
<P style="LINE-HEIGHT: normal; MARGIN: 0in 0in 0pt; mso-layout-grid-align: none" class=MsoNormal><SPAN style="FONT-FAMILY: NSimSun; FONT-SIZE: 9.5pt; mso-bidi-font-family: NSimSun"><SPAN style="mso-spacerun: yes">&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp; </SPAN>()=&gt;<SPAN style="COLOR: #2b91af">Console</SPAN>.WriteLine(<SPAN style="COLOR: #a31515">"hello"</SPAN>),<o:p></o:p></SPAN></P>
<P style="LINE-HEIGHT: normal; MARGIN: 0in 0in 0pt; mso-layout-grid-align: none" class=MsoNormal><SPAN style="FONT-FAMILY: NSimSun; FONT-SIZE: 9.5pt; mso-bidi-font-family: NSimSun"><SPAN style="mso-spacerun: yes">&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp; </SPAN>()=&gt;<SPAN style="COLOR: #2b91af">Console</SPAN>.WriteLine(<SPAN style="COLOR: #a31515">"world!"</SPAN>)<o:p></o:p></SPAN></P>
<P style="LINE-HEIGHT: normal; MARGIN: 0in 0in 0pt; mso-layout-grid-align: none" class=MsoNormal><SPAN style="FONT-FAMILY: NSimSun; FONT-SIZE: 9.5pt; mso-bidi-font-family: NSimSun"><SPAN style="mso-spacerun: yes">&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp; </SPAN>);<o:p></o:p></SPAN></P>
<P style="MARGIN: 0in 0in 10pt" class=MsoCaption><STRONG><FONT color=#4f81bd><FONT face=Calibri><SPAN style="mso-spacerun: yes">&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp; </SPAN>Code <SPAN style="mso-no-proof: yes">17. calling the C# Sequence method with delegates</SPAN></FONT></FONT></STRONG></P>
<P style="MARGIN: 0in 0in 10pt" class=MsoNormal><FONT size=3><FONT face=Calibri>As illustrated, from Sequence’s point of view, it’s children activities are actually from outside. In WF term, we call this type of children “public children”, versus “implementation children” which is purely defined by the parent activity itself. When an Activity declares its children Activities in CacheMetadata, it needs to say whether a child is “public” or “implementation” (personally I don’t like the word “public” in this context because it reminds people for the “public” keyword in OO languages but means something totally different). <o:p></o:p></FONT></FONT></P>
<P style="MARGIN: 0in 0in 10pt" class=MsoNormal><FONT size=3><FONT face=Calibri>What if those public child Activities want to share some data? Naturally they should use variables. But those variables could not be defined by the parent Activity since it wouldn’t even know what the public children are, let alone the data they want to share. Again, I could illustrate the idea with C# code:<o:p></o:p></FONT></FONT></P>
<P style="LINE-HEIGHT: normal; MARGIN: 0in 0in 0pt; mso-layout-grid-align: none" class=MsoNormal><SPAN style="FONT-FAMILY: NSimSun; COLOR: blue; FONT-SIZE: 9.5pt; mso-bidi-font-family: NSimSun"><SPAN style="mso-spacerun: yes">&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp; </SPAN><SPAN style="mso-spacerun: yes">&nbsp;</SPAN>static</SPAN><SPAN style="FONT-FAMILY: NSimSun; FONT-SIZE: 9.5pt; mso-bidi-font-family: NSimSun"> <SPAN style="COLOR: blue">void</SPAN> Sequence(<SPAN style="COLOR: blue">params</SPAN> <SPAN style="COLOR: #2b91af">Action</SPAN>[] statements)<o:p></o:p></SPAN></P>
<P style="LINE-HEIGHT: normal; MARGIN: 0in 0in 0pt; mso-layout-grid-align: none" class=MsoNormal><SPAN style="FONT-FAMILY: NSimSun; FONT-SIZE: 9.5pt; mso-bidi-font-family: NSimSun"><SPAN style="mso-spacerun: yes">&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp; </SPAN>{<SPAN style="mso-spacerun: yes">&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp; </SPAN><o:p></o:p></SPAN></P>
<P style="LINE-HEIGHT: normal; MARGIN: 0in 0in 0pt; mso-layout-grid-align: none" class=MsoNormal><SPAN style="FONT-FAMILY: NSimSun; FONT-SIZE: 9.5pt; mso-bidi-font-family: NSimSun"><SPAN style="mso-spacerun: yes">&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp; </SPAN><SPAN style="COLOR: green">//tries to access the variable defined outside the method <o:p></o:p></SPAN></SPAN></P>
<P style="LINE-HEIGHT: normal; MARGIN: 0in 0in 0pt; mso-layout-grid-align: none" class=MsoNormal><SPAN style="FONT-FAMILY: NSimSun; COLOR: green; FONT-SIZE: 9.5pt; mso-bidi-font-family: NSimSun"><SPAN style="mso-spacerun: yes">&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp; </SPAN>//this does not compile!</SPAN><SPAN style="FONT-FAMILY: NSimSun; FONT-SIZE: 9.5pt; mso-bidi-font-family: NSimSun"><o:p></o:p></SPAN></P>
<P style="LINE-HEIGHT: normal; MARGIN: 0in 0in 0pt; mso-layout-grid-align: none" class=MsoNormal><SPAN style="FONT-FAMILY: NSimSun; FONT-SIZE: 9.5pt; mso-bidi-font-family: NSimSun"><SPAN style="mso-spacerun: yes">&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp; </SPAN><SPAN style="COLOR: green">//outside = 5;<SPAN style="mso-spacerun: yes">&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp; </SPAN></SPAN><o:p></o:p></SPAN></P>
<P style="LINE-HEIGHT: normal; MARGIN: 0in 0in 0pt; mso-layout-grid-align: none" class=MsoNormal><SPAN style="FONT-FAMILY: NSimSun; FONT-SIZE: 9.5pt; mso-bidi-font-family: NSimSun"><SPAN style="mso-spacerun: yes">&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp; </SPAN><SPAN style="COLOR: blue">int</SPAN> inside = 5;<o:p></o:p></SPAN></P>
<P style="LINE-HEIGHT: normal; MARGIN: 0in 0in 0pt; mso-layout-grid-align: none" class=MsoNormal><SPAN style="FONT-FAMILY: NSimSun; FONT-SIZE: 9.5pt; mso-bidi-font-family: NSimSun"><SPAN style="mso-spacerun: yes">&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp; </SPAN><SPAN style="COLOR: blue">foreach</SPAN> (<SPAN style="COLOR: #2b91af">Action</SPAN> statement <SPAN style="COLOR: blue">in</SPAN> statements)<o:p></o:p></SPAN></P>
<P style="LINE-HEIGHT: normal; MARGIN: 0in 0in 0pt; mso-layout-grid-align: none" class=MsoNormal><SPAN style="FONT-FAMILY: NSimSun; FONT-SIZE: 9.5pt; mso-bidi-font-family: NSimSun"><SPAN style="mso-spacerun: yes">&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp; </SPAN>{<o:p></o:p></SPAN></P>
<P style="LINE-HEIGHT: normal; MARGIN: 0in 0in 0pt; mso-layout-grid-align: none" class=MsoNormal><SPAN style="FONT-FAMILY: NSimSun; FONT-SIZE: 9.5pt; mso-bidi-font-family: NSimSun"><SPAN style="mso-spacerun: yes">&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp; </SPAN>statement();<o:p></o:p></SPAN></P>
<P style="LINE-HEIGHT: normal; MARGIN: 0in 0in 0pt; mso-layout-grid-align: none" class=MsoNormal><SPAN style="FONT-FAMILY: NSimSun; FONT-SIZE: 9.5pt; mso-bidi-font-family: NSimSun"><SPAN style="mso-spacerun: yes">&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp; </SPAN>}<o:p></o:p></SPAN></P>
<P style="LINE-HEIGHT: normal; MARGIN: 0in 0in 0pt; mso-layout-grid-align: none" class=MsoNormal><SPAN style="FONT-FAMILY: NSimSun; FONT-SIZE: 9.5pt; mso-bidi-font-family: NSimSun"><SPAN style="mso-spacerun: yes">&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp; </SPAN>}<o:p></o:p></SPAN></P>
<P style="LINE-HEIGHT: normal; MARGIN: 0in 0in 0pt; mso-layout-grid-align: none" class=MsoNormal><o:p><FONT size=3 face=Calibri>&nbsp;</FONT></o:p></P>
<P style="LINE-HEIGHT: normal; MARGIN: 0in 0in 0pt; mso-layout-grid-align: none" class=MsoNormal><SPAN style="mso-spacerun: yes"><FONT size=3 face=Calibri>&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp; </FONT></SPAN><SPAN style="FONT-FAMILY: NSimSun; COLOR: green; FONT-SIZE: 9.5pt; mso-bidi-font-family: NSimSun">//to call the sequence with statements sharing a variable</SPAN><SPAN style="FONT-FAMILY: NSimSun; FONT-SIZE: 9.5pt; mso-bidi-font-family: NSimSun"><o:p></o:p></SPAN></P>
<P style="LINE-HEIGHT: normal; MARGIN: 0in 0in 0pt; mso-layout-grid-align: none" class=MsoNormal><SPAN style="FONT-FAMILY: NSimSun; FONT-SIZE: 9.5pt; mso-bidi-font-family: NSimSun"><SPAN style="mso-spacerun: yes">&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp; </SPAN><SPAN style="COLOR: blue">int</SPAN> outside = 0;<o:p></o:p></SPAN></P>
<P style="LINE-HEIGHT: normal; MARGIN: 0in 0in 0pt; mso-layout-grid-align: none" class=MsoNormal><SPAN style="FONT-FAMILY: NSimSun; FONT-SIZE: 9.5pt; mso-bidi-font-family: NSimSun"><SPAN style="mso-spacerun: yes">&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp; </SPAN>Sequence(<o:p></o:p></SPAN></P>
<P style="LINE-HEIGHT: normal; MARGIN: 0in 0in 0pt; mso-layout-grid-align: none" class=MsoNormal><SPAN style="FONT-FAMILY: NSimSun; FONT-SIZE: 9.5pt; mso-bidi-font-family: NSimSun"><SPAN style="mso-spacerun: yes">&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp; </SPAN>()=&gt;<SPAN style="COLOR: #2b91af">Console</SPAN>.WriteLine (outside++),<o:p></o:p></SPAN></P>
<P style="LINE-HEIGHT: normal; MARGIN: 0in 0in 0pt; mso-layout-grid-align: none" class=MsoNormal><SPAN style="FONT-FAMILY: NSimSun; FONT-SIZE: 9.5pt; mso-bidi-font-family: NSimSun"><SPAN style="mso-spacerun: yes">&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp; </SPAN>() =&gt; <SPAN style="COLOR: #2b91af">Console</SPAN>.WriteLine(outside++),<o:p></o:p></SPAN></P>
<P style="LINE-HEIGHT: normal; MARGIN: 0in 0in 0pt; mso-layout-grid-align: none" class=MsoNormal><SPAN style="FONT-FAMILY: NSimSun; FONT-SIZE: 9.5pt; mso-bidi-font-family: NSimSun"><SPAN style="mso-spacerun: yes">&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp; </SPAN>() =&gt; <SPAN style="COLOR: #2b91af">Console</SPAN>.WriteLine(outside++),<o:p></o:p></SPAN></P>
<P style="LINE-HEIGHT: normal; MARGIN: 0in 0in 0pt; mso-layout-grid-align: none" class=MsoNormal><SPAN style="FONT-FAMILY: NSimSun; FONT-SIZE: 9.5pt; mso-bidi-font-family: NSimSun"><SPAN style="mso-spacerun: yes">&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp; </SPAN>() =&gt; <SPAN style="COLOR: #2b91af">Console</SPAN>.WriteLine(outside++)<o:p></o:p></SPAN></P>
<P style="LINE-HEIGHT: normal; MARGIN: 0in 0in 0pt; mso-layout-grid-align: none" class=MsoNormal><SPAN style="FONT-FAMILY: NSimSun; FONT-SIZE: 9.5pt; mso-bidi-font-family: NSimSun"><SPAN style="mso-spacerun: yes">&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp; </SPAN><SPAN style="COLOR: green">//tries to access a variable defined inside the method,<o:p></o:p></SPAN></SPAN></P>
<P style="LINE-HEIGHT: normal; MARGIN: 0in 0in 0pt; mso-layout-grid-align: none" class=MsoNormal><SPAN style="FONT-FAMILY: NSimSun; COLOR: green; FONT-SIZE: 9.5pt; mso-bidi-font-family: NSimSun"><SPAN style="mso-spacerun: yes">&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp; </SPAN>//this does not compile!</SPAN><SPAN style="FONT-FAMILY: NSimSun; FONT-SIZE: 9.5pt; mso-bidi-font-family: NSimSun"><o:p></o:p></SPAN></P>
<P style="LINE-HEIGHT: normal; MARGIN: 0in 0in 0pt; mso-layout-grid-align: none" class=MsoNormal><SPAN style="FONT-FAMILY: NSimSun; FONT-SIZE: 9.5pt; mso-bidi-font-family: NSimSun"><SPAN style="mso-spacerun: yes">&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp; </SPAN><SPAN style="COLOR: green">//,() =&gt; Console.WriteLine(inside)</SPAN><o:p></o:p></SPAN></P>
<P style="LINE-HEIGHT: normal; MARGIN: 0in 0in 0pt; mso-layout-grid-align: none" class=MsoNormal><SPAN style="FONT-FAMILY: NSimSun; FONT-SIZE: 9.5pt; mso-bidi-font-family: NSimSun"><SPAN style="mso-spacerun: yes">&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp; </SPAN>);<o:p></o:p></SPAN></P>
<P style="MARGIN: 0in 0in 10pt" class=MsoCaption><STRONG><FONT color=#4f81bd><FONT face=Calibri><SPAN style="mso-spacerun: yes">&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp; </SPAN>Code <SPAN style="mso-no-proof: yes">18. illustrate how "public" children share data using C# code</SPAN></FONT></FONT></STRONG></P>
<P style="MARGIN: 0in 0in 10pt" class=MsoNormal><FONT size=3><FONT face=Calibri>As we could see, variables used by “public” statements have to be defined outside of method, and not visible to implementation of the method. WF programming model allow such variables to be declared on the parent Activity itself as “public variables”. For example, class Sequence is defined this way:<o:p></o:p></FONT></FONT></P>
<P style="LINE-HEIGHT: normal; MARGIN: 0in 0in 0pt; mso-layout-grid-align: none" class=MsoNormal><SPAN style="FONT-FAMILY: NSimSun; COLOR: blue; FONT-SIZE: 9.5pt; mso-bidi-font-family: NSimSun"><SPAN style="mso-spacerun: yes">&nbsp;&nbsp;&nbsp; </SPAN>public</SPAN><SPAN style="FONT-FAMILY: NSimSun; FONT-SIZE: 9.5pt; mso-bidi-font-family: NSimSun"> <SPAN style="COLOR: blue">sealed</SPAN> <SPAN style="COLOR: blue">class</SPAN> <SPAN style="COLOR: #2b91af">Sequence</SPAN> : <SPAN style="COLOR: #2b91af">NativeActivity</SPAN><o:p></o:p></SPAN></P>
<P style="LINE-HEIGHT: normal; MARGIN: 0in 0in 0pt; mso-layout-grid-align: none" class=MsoNormal><SPAN style="FONT-FAMILY: NSimSun; FONT-SIZE: 9.5pt; mso-bidi-font-family: NSimSun"><SPAN style="mso-spacerun: yes">&nbsp;&nbsp;&nbsp; </SPAN>{<o:p></o:p></SPAN></P>
<P style="LINE-HEIGHT: normal; MARGIN: 0in 0in 0pt; mso-layout-grid-align: none" class=MsoNormal><SPAN style="FONT-FAMILY: NSimSun; FONT-SIZE: 9.5pt; mso-bidi-font-family: NSimSun"><SPAN style="mso-spacerun: yes">&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp; </SPAN><SPAN style="COLOR: blue">public</SPAN> <SPAN style="COLOR: #2b91af">Collection</SPAN>&lt;<SPAN style="COLOR: #2b91af">Activity</SPAN>&gt; Activities { <SPAN style="COLOR: blue">get</SPAN>; }<o:p></o:p></SPAN></P>
<P style="LINE-HEIGHT: normal; MARGIN: 0in 0in 0pt; mso-layout-grid-align: none" class=MsoNormal><SPAN style="FONT-FAMILY: NSimSun; FONT-SIZE: 9.5pt; mso-bidi-font-family: NSimSun"><SPAN style="mso-spacerun: yes">&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp; </SPAN><SPAN style="COLOR: blue">public</SPAN> <SPAN style="COLOR: #2b91af">Collection</SPAN>&lt;<SPAN style="COLOR: #2b91af">Variable</SPAN>&gt; Variables { <SPAN style="COLOR: blue">get</SPAN>; }<o:p></o:p></SPAN></P>
<P style="LINE-HEIGHT: normal; MARGIN: 0in 0in 0pt; mso-layout-grid-align: none" class=MsoNormal><SPAN style="FONT-FAMILY: NSimSun; FONT-SIZE: 9.5pt; mso-bidi-font-family: NSimSun"><SPAN style="mso-spacerun: yes">&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp; </SPAN>…<o:p></o:p></SPAN></P>
<P style="LINE-HEIGHT: normal; MARGIN: 0in 0in 0pt; mso-layout-grid-align: none" class=MsoNormal><SPAN style="FONT-FAMILY: NSimSun; FONT-SIZE: 9.5pt; mso-bidi-font-family: NSimSun"><SPAN style="mso-spacerun: yes">&nbsp;&nbsp;&nbsp; </SPAN>}<o:p></o:p></SPAN></P>
<P style="MARGIN: 0in 0in 10pt" class=MsoCaption><STRONG><FONT color=#4f81bd><FONT face=Calibri><SPAN style="mso-spacerun: yes">&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp; </SPAN>Code <SPAN style="mso-no-proof: yes">19. Sequence Activity interface</SPAN><o:p></o:p></FONT></FONT></STRONG></P>
<P style="MARGIN: 0in 0in 10pt" class=MsoNormal><FONT size=3><FONT face=Calibri>The Variables collection holds a list of “public” variables which could be defined by users of Sequence and accessible by its “public” child Activities. <o:p></o:p></FONT></FONT></P>
<P style="MARGIN: 0in 0in 10pt" class=MsoNormal><FONT size=3><FONT face=Calibri>If an Activity needs some bookkeeping data for its own execution, it could declare it as an “implementation” variable and no need to expose it as a public property on the class in general.<o:p></o:p></FONT></FONT></P>
<P style="MARGIN: 0in 0in 10pt" class=MsoNormal><FONT size=3><FONT face=Calibri>Here is an example to demo how to declare public and implementation variables plus difference between them:<o:p></o:p></FONT></FONT></P>
<P style="LINE-HEIGHT: normal; MARGIN: 0in 0in 0pt; mso-layout-grid-align: none" class=MsoNormal><SPAN style="FONT-FAMILY: NSimSun; COLOR: blue; FONT-SIZE: 9.5pt; mso-bidi-font-family: NSimSun"><SPAN style="mso-spacerun: yes">&nbsp;&nbsp;&nbsp; </SPAN>public</SPAN><SPAN style="FONT-FAMILY: NSimSun; FONT-SIZE: 9.5pt; mso-bidi-font-family: NSimSun"> <SPAN style="COLOR: blue">class</SPAN> <SPAN style="COLOR: #2b91af">MySquence</SPAN> : <SPAN style="COLOR: #2b91af">NativeActivity</SPAN><o:p></o:p></SPAN></P>
<P style="LINE-HEIGHT: normal; MARGIN: 0in 0in 0pt; mso-layout-grid-align: none" class=MsoNormal><SPAN style="FONT-FAMILY: NSimSun; FONT-SIZE: 9.5pt; mso-bidi-font-family: NSimSun"><SPAN style="mso-spacerun: yes">&nbsp;&nbsp;&nbsp; </SPAN>{<o:p></o:p></SPAN></P>
<P style="LINE-HEIGHT: normal; MARGIN: 0in 0in 0pt; mso-layout-grid-align: none" class=MsoNormal><SPAN style="FONT-FAMILY: NSimSun; FONT-SIZE: 9.5pt; mso-bidi-font-family: NSimSun"><SPAN style="mso-spacerun: yes">&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp; </SPAN><SPAN style="COLOR: green">//this is an implementation variable, no need to expose to users</SPAN><o:p></o:p></SPAN></P>
<P style="LINE-HEIGHT: normal; MARGIN: 0in 0in 0pt; mso-layout-grid-align: none" class=MsoNormal><SPAN style="FONT-FAMILY: NSimSun; FONT-SIZE: 9.5pt; mso-bidi-font-family: NSimSun"><SPAN style="mso-spacerun: yes">&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp; </SPAN><SPAN style="COLOR: #2b91af">Variable</SPAN>&lt;<SPAN style="COLOR: blue">int</SPAN>&gt; index = <SPAN style="COLOR: blue">new</SPAN> <SPAN style="COLOR: #2b91af">Variable</SPAN>&lt;<SPAN style="COLOR: blue">int</SPAN>&gt;();<SPAN style="mso-spacerun: yes">&nbsp;&nbsp; </SPAN><o:p></o:p></SPAN></P>
<P style="LINE-HEIGHT: normal; MARGIN: 0in 0in 0pt; mso-layout-grid-align: none" class=MsoNormal><SPAN style="FONT-FAMILY: NSimSun; FONT-SIZE: 9.5pt; mso-bidi-font-family: NSimSun"><SPAN style="mso-spacerun: yes">&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp; </SPAN><o:p></o:p></SPAN></P>
<P style="LINE-HEIGHT: normal; MARGIN: 0in 0in 0pt; mso-layout-grid-align: none" class=MsoNormal><SPAN style="FONT-FAMILY: NSimSun; FONT-SIZE: 9.5pt; mso-bidi-font-family: NSimSun"><SPAN style="mso-spacerun: yes">&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp; </SPAN><SPAN style="COLOR: green">//a collection of public child activities for users to fill</SPAN><o:p></o:p></SPAN></P>
<P style="LINE-HEIGHT: normal; MARGIN: 0in 0in 0pt; mso-layout-grid-align: none" class=MsoNormal><SPAN style="FONT-FAMILY: NSimSun; FONT-SIZE: 9.5pt; mso-bidi-font-family: NSimSun"><SPAN style="mso-spacerun: yes">&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp; </SPAN><SPAN style="COLOR: #2b91af">Collection</SPAN>&lt;<SPAN style="COLOR: #2b91af">Activity</SPAN>&gt; activities = <SPAN style="COLOR: blue">new</SPAN> <SPAN style="COLOR: #2b91af">Collection</SPAN>&lt;<SPAN style="COLOR: #2b91af">Activity</SPAN>&gt;();<o:p></o:p></SPAN></P>
<P style="LINE-HEIGHT: normal; MARGIN: 0in 0in 0pt; mso-layout-grid-align: none" class=MsoNormal><SPAN style="FONT-FAMILY: NSimSun; FONT-SIZE: 9.5pt; mso-bidi-font-family: NSimSun"><SPAN style="mso-spacerun: yes">&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp; </SPAN><SPAN style="COLOR: blue">public</SPAN> <SPAN style="COLOR: #2b91af">Collection</SPAN>&lt;<SPAN style="COLOR: #2b91af">Activity</SPAN>&gt; Activities<o:p></o:p></SPAN></P>
<P style="LINE-HEIGHT: normal; MARGIN: 0in 0in 0pt; mso-layout-grid-align: none" class=MsoNormal><SPAN style="FONT-FAMILY: NSimSun; FONT-SIZE: 9.5pt; mso-bidi-font-family: NSimSun"><SPAN style="mso-spacerun: yes">&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp; </SPAN>{<o:p></o:p></SPAN></P>
<P style="LINE-HEIGHT: normal; MARGIN: 0in 0in 0pt; mso-layout-grid-align: none" class=MsoNormal><SPAN style="FONT-FAMILY: NSimSun; FONT-SIZE: 9.5pt; mso-bidi-font-family: NSimSun"><SPAN style="mso-spacerun: yes">&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp; </SPAN><SPAN style="COLOR: blue">get</SPAN> { <SPAN style="COLOR: blue">return</SPAN> <SPAN style="COLOR: blue">this</SPAN>.activities; }<o:p></o:p></SPAN></P>
<P style="LINE-HEIGHT: normal; MARGIN: 0in 0in 0pt; mso-layout-grid-align: none" class=MsoNormal><SPAN style="FONT-FAMILY: NSimSun; FONT-SIZE: 9.5pt; mso-bidi-font-family: NSimSun"><SPAN style="mso-spacerun: yes">&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp; </SPAN>}<o:p></o:p></SPAN></P>
<P style="LINE-HEIGHT: normal; MARGIN: 0in 0in 0pt; mso-layout-grid-align: none" class=MsoNormal><SPAN style="FONT-FAMILY: NSimSun; FONT-SIZE: 9.5pt; mso-bidi-font-family: NSimSun"><o:p>&nbsp;</o:p></SPAN></P>
<P style="LINE-HEIGHT: normal; MARGIN: 0in 0in 0pt; mso-layout-grid-align: none" class=MsoNormal><SPAN style="FONT-FAMILY: NSimSun; FONT-SIZE: 9.5pt; mso-bidi-font-family: NSimSun"><SPAN style="mso-spacerun: yes">&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp; </SPAN><SPAN style="COLOR: green">//a collectoin of public variables for users to fill</SPAN><o:p></o:p></SPAN></P>
<P style="LINE-HEIGHT: normal; MARGIN: 0in 0in 0pt; mso-layout-grid-align: none" class=MsoNormal><SPAN style="FONT-FAMILY: NSimSun; FONT-SIZE: 9.5pt; mso-bidi-font-family: NSimSun"><SPAN style="mso-spacerun: yes">&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp; </SPAN><SPAN style="COLOR: #2b91af">Collection</SPAN>&lt;<SPAN style="COLOR: #2b91af">Variable</SPAN>&gt; variables = <SPAN style="COLOR: blue">new</SPAN> <SPAN style="COLOR: #2b91af">Collection</SPAN>&lt;<SPAN style="COLOR: #2b91af">Variable</SPAN>&gt;();<o:p></o:p></SPAN></P>
<P style="LINE-HEIGHT: normal; MARGIN: 0in 0in 0pt; mso-layout-grid-align: none" class=MsoNormal><SPAN style="FONT-FAMILY: NSimSun; FONT-SIZE: 9.5pt; mso-bidi-font-family: NSimSun"><SPAN style="mso-spacerun: yes">&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp; </SPAN><SPAN style="COLOR: blue">public</SPAN> <SPAN style="COLOR: #2b91af">Collection</SPAN>&lt;<SPAN style="COLOR: #2b91af">Variable</SPAN>&gt; Variables<o:p></o:p></SPAN></P>
<P style="LINE-HEIGHT: normal; MARGIN: 0in 0in 0pt; mso-layout-grid-align: none" class=MsoNormal><SPAN style="FONT-FAMILY: NSimSun; FONT-SIZE: 9.5pt; mso-bidi-font-family: NSimSun"><SPAN style="mso-spacerun: yes">&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp; </SPAN>{<o:p></o:p></SPAN></P>
<P style="LINE-HEIGHT: normal; MARGIN: 0in 0in 0pt; mso-layout-grid-align: none" class=MsoNormal><SPAN style="FONT-FAMILY: NSimSun; FONT-SIZE: 9.5pt; mso-bidi-font-family: NSimSun"><SPAN style="mso-spacerun: yes">&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp; </SPAN><SPAN style="COLOR: blue">get</SPAN> { <SPAN style="COLOR: blue">return</SPAN> <SPAN style="COLOR: blue">this</SPAN>.variables; }<o:p></o:p></SPAN></P>
<P style="LINE-HEIGHT: normal; MARGIN: 0in 0in 0pt; mso-layout-grid-align: none" class=MsoNormal><SPAN style="FONT-FAMILY: NSimSun; FONT-SIZE: 9.5pt; mso-bidi-font-family: NSimSun"><SPAN style="mso-spacerun: yes">&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp; </SPAN>}<o:p></o:p></SPAN></P>
<P style="LINE-HEIGHT: normal; MARGIN: 0in 0in 0pt; mso-layout-grid-align: none" class=MsoNormal><SPAN style="FONT-FAMILY: NSimSun; FONT-SIZE: 9.5pt; mso-bidi-font-family: NSimSun"><o:p>&nbsp;</o:p></SPAN></P>
<P style="LINE-HEIGHT: normal; MARGIN: 0in 0in 0pt; mso-layout-grid-align: none" class=MsoNormal><SPAN style="FONT-FAMILY: NSimSun; FONT-SIZE: 9.5pt; mso-bidi-font-family: NSimSun"><SPAN style="mso-spacerun: yes">&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp; </SPAN><SPAN style="COLOR: blue">protected</SPAN> <SPAN style="COLOR: blue">override</SPAN> <SPAN style="COLOR: blue">void</SPAN> CacheMetadata(<SPAN style="COLOR: #2b91af">NativeActivityMetadata</SPAN> metadata)<o:p></o:p></SPAN></P>
<P style="LINE-HEIGHT: normal; MARGIN: 0in 0in 0pt; mso-layout-grid-align: none" class=MsoNormal><SPAN style="FONT-FAMILY: NSimSun; FONT-SIZE: 9.5pt; mso-bidi-font-family: NSimSun"><SPAN style="mso-spacerun: yes">&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp; </SPAN>{<o:p></o:p></SPAN></P>
<P style="LINE-HEIGHT: normal; MARGIN: 0in 0in 0pt; mso-layout-grid-align: none" class=MsoNormal><SPAN style="FONT-FAMILY: NSimSun; FONT-SIZE: 9.5pt; mso-bidi-font-family: NSimSun"><SPAN style="mso-spacerun: yes">&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp; </SPAN><SPAN style="COLOR: green">//base.CacheMetadata(metadata);</SPAN><o:p></o:p></SPAN></P>
<P style="LINE-HEIGHT: normal; MARGIN: 0in 0in 0pt; mso-layout-grid-align: none" class=MsoNormal><SPAN style="FONT-FAMILY: NSimSun; FONT-SIZE: 9.5pt; mso-bidi-font-family: NSimSun"><SPAN style="mso-spacerun: yes">&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp; </SPAN><SPAN style="COLOR: blue">foreach</SPAN> (<SPAN style="COLOR: #2b91af">Activity</SPAN> child <SPAN style="COLOR: blue">in</SPAN> <SPAN style="COLOR: blue">this</SPAN>.Activities)<o:p></o:p></SPAN></P>
<P style="LINE-HEIGHT: normal; MARGIN: 0in 0in 0pt; mso-layout-grid-align: none" class=MsoNormal><SPAN style="FONT-FAMILY: NSimSun; FONT-SIZE: 9.5pt; mso-bidi-font-family: NSimSun"><SPAN style="mso-spacerun: yes">&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp; </SPAN>{<o:p></o:p></SPAN></P>
<P style="LINE-HEIGHT: normal; MARGIN: 0in 0in 0pt; mso-layout-grid-align: none" class=MsoNormal><SPAN style="FONT-FAMILY: NSimSun; FONT-SIZE: 9.5pt; mso-bidi-font-family: NSimSun"><SPAN style="mso-spacerun: yes">&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp; </SPAN><SPAN style="COLOR: green">//declare a public child Activity</SPAN><o:p></o:p></SPAN></P>
<P style="LINE-HEIGHT: normal; MARGIN: 0in 0in 0pt; mso-layout-grid-align: none" class=MsoNormal><SPAN style="FONT-FAMILY: NSimSun; FONT-SIZE: 9.5pt; mso-bidi-font-family: NSimSun"><SPAN style="mso-spacerun: yes">&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp; </SPAN>metadata.AddChild(child);<o:p></o:p></SPAN></P>
<P style="LINE-HEIGHT: normal; MARGIN: 0in 0in 0pt; mso-layout-grid-align: none" class=MsoNormal><SPAN style="FONT-FAMILY: NSimSun; FONT-SIZE: 9.5pt; mso-bidi-font-family: NSimSun"><SPAN style="mso-spacerun: yes">&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp; </SPAN>}<o:p></o:p></SPAN></P>
<P style="LINE-HEIGHT: normal; MARGIN: 0in 0in 0pt; mso-layout-grid-align: none" class=MsoNormal><SPAN style="FONT-FAMILY: NSimSun; FONT-SIZE: 9.5pt; mso-bidi-font-family: NSimSun"><SPAN style="mso-spacerun: yes">&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp; </SPAN><SPAN style="COLOR: blue">foreach</SPAN> (<SPAN style="COLOR: #2b91af">Variable</SPAN> variable <SPAN style="COLOR: blue">in</SPAN> <SPAN style="COLOR: blue">this</SPAN>.Variables)<o:p></o:p></SPAN></P>
<P style="LINE-HEIGHT: normal; MARGIN: 0in 0in 0pt; mso-layout-grid-align: none" class=MsoNormal><SPAN style="FONT-FAMILY: NSimSun; FONT-SIZE: 9.5pt; mso-bidi-font-family: NSimSun"><SPAN style="mso-spacerun: yes">&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp; </SPAN>{<o:p></o:p></SPAN></P>
<P style="LINE-HEIGHT: normal; MARGIN: 0in 0in 0pt; mso-layout-grid-align: none" class=MsoNormal><SPAN style="FONT-FAMILY: NSimSun; FONT-SIZE: 9.5pt; mso-bidi-font-family: NSimSun"><SPAN style="mso-spacerun: yes">&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp; </SPAN><SPAN style="COLOR: green">//declare a public variable</SPAN><o:p></o:p></SPAN></P>
<P style="LINE-HEIGHT: normal; MARGIN: 0in 0in 0pt; mso-layout-grid-align: none" class=MsoNormal><SPAN style="FONT-FAMILY: NSimSun; FONT-SIZE: 9.5pt; mso-bidi-font-family: NSimSun"><SPAN style="mso-spacerun: yes">&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp; </SPAN>metadata.AddVariable(variable);<o:p></o:p></SPAN></P>
<P style="LINE-HEIGHT: normal; MARGIN: 0in 0in 0pt; mso-layout-grid-align: none" class=MsoNormal><SPAN style="FONT-FAMILY: NSimSun; FONT-SIZE: 9.5pt; mso-bidi-font-family: NSimSun"><SPAN style="mso-spacerun: yes">&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp; </SPAN>}<o:p></o:p></SPAN></P>
<P style="LINE-HEIGHT: normal; MARGIN: 0in 0in 0pt; mso-layout-grid-align: none" class=MsoNormal><SPAN style="FONT-FAMILY: NSimSun; FONT-SIZE: 9.5pt; mso-bidi-font-family: NSimSun"><SPAN style="mso-spacerun: yes">&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp; </SPAN><SPAN style="COLOR: green">//declare a implementation variable</SPAN><o:p></o:p></SPAN></P>
<P style="LINE-HEIGHT: normal; MARGIN: 0in 0in 0pt; mso-layout-grid-align: none" class=MsoNormal><SPAN style="FONT-FAMILY: NSimSun; FONT-SIZE: 9.5pt; mso-bidi-font-family: NSimSun"><SPAN style="mso-spacerun: yes">&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp; </SPAN>metadata.AddImplementationVariable(<SPAN style="COLOR: blue">this</SPAN>.index);<o:p></o:p></SPAN></P>
<P style="LINE-HEIGHT: normal; MARGIN: 0in 0in 0pt; mso-layout-grid-align: none" class=MsoNormal><SPAN style="FONT-FAMILY: NSimSun; FONT-SIZE: 9.5pt; mso-bidi-font-family: NSimSun"><SPAN style="mso-spacerun: yes">&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp; </SPAN>}<o:p></o:p></SPAN></P>
<P style="LINE-HEIGHT: normal; MARGIN: 0in 0in 0pt; mso-layout-grid-align: none" class=MsoNormal><SPAN style="FONT-FAMILY: NSimSun; FONT-SIZE: 9.5pt; mso-bidi-font-family: NSimSun"><o:p>&nbsp;</o:p></SPAN></P>
<P style="LINE-HEIGHT: normal; MARGIN: 0in 0in 0pt; mso-layout-grid-align: none" class=MsoNormal><SPAN style="FONT-FAMILY: NSimSun; FONT-SIZE: 9.5pt; mso-bidi-font-family: NSimSun"><SPAN style="mso-spacerun: yes">&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp; </SPAN><SPAN style="COLOR: blue">protected</SPAN> <SPAN style="COLOR: blue">override</SPAN> <SPAN style="COLOR: blue">void</SPAN> Execute(<SPAN style="COLOR: #2b91af">NativeActivityContext</SPAN> context)<o:p></o:p></SPAN></P>
<P style="LINE-HEIGHT: normal; MARGIN: 0in 0in 0pt; mso-layout-grid-align: none" class=MsoNormal><SPAN style="FONT-FAMILY: NSimSun; FONT-SIZE: 9.5pt; mso-bidi-font-family: NSimSun"><SPAN style="mso-spacerun: yes">&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp; </SPAN>{<o:p></o:p></SPAN></P>
<P style="LINE-HEIGHT: normal; MARGIN: 0in 0in 0pt; mso-layout-grid-align: none" class=MsoNormal><SPAN style="FONT-FAMILY: NSimSun; FONT-SIZE: 9.5pt; mso-bidi-font-family: NSimSun"><SPAN style="mso-spacerun: yes">&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp; </SPAN><SPAN style="COLOR: green">//store data in the implementation variable</SPAN><o:p></o:p></SPAN></P>
<P style="LINE-HEIGHT: normal; MARGIN: 0in 0in 0pt; mso-layout-grid-align: none" class=MsoNormal><SPAN style="FONT-FAMILY: NSimSun; FONT-SIZE: 9.5pt; mso-bidi-font-family: NSimSun"><SPAN style="mso-spacerun: yes">&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp; </SPAN><SPAN style="COLOR: blue">this</SPAN>.index.Set(context, 0);<o:p></o:p></SPAN></P>
<P style="LINE-HEIGHT: normal; MARGIN: 0in 0in 0pt; mso-layout-grid-align: none" class=MsoNormal><SPAN style="FONT-FAMILY: NSimSun; FONT-SIZE: 9.5pt; mso-bidi-font-family: NSimSun"><SPAN style="mso-spacerun: yes">&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp; </SPAN>ScheduleNextChild(context);<o:p></o:p></SPAN></P>
<P style="LINE-HEIGHT: normal; MARGIN: 0in 0in 0pt; mso-layout-grid-align: none" class=MsoNormal><SPAN style="FONT-FAMILY: NSimSun; FONT-SIZE: 9.5pt; mso-bidi-font-family: NSimSun"><SPAN style="mso-spacerun: yes">&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp; </SPAN>}<o:p></o:p></SPAN></P>
<P style="LINE-HEIGHT: normal; MARGIN: 0in 0in 0pt; mso-layout-grid-align: none" class=MsoNormal><SPAN style="FONT-FAMILY: NSimSun; FONT-SIZE: 9.5pt; mso-bidi-font-family: NSimSun"><o:p>&nbsp;</o:p></SPAN></P>
<P style="LINE-HEIGHT: normal; MARGIN: 0in 0in 0pt; mso-layout-grid-align: none" class=MsoNormal><SPAN style="FONT-FAMILY: NSimSun; FONT-SIZE: 9.5pt; mso-bidi-font-family: NSimSun"><SPAN style="mso-spacerun: yes">&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp; </SPAN><SPAN style="COLOR: blue">void</SPAN> ScheduleNextChild(<SPAN style="COLOR: #2b91af">NativeActivityContext</SPAN> context)<o:p></o:p></SPAN></P>
<P style="LINE-HEIGHT: normal; MARGIN: 0in 0in 0pt; mso-layout-grid-align: none" class=MsoNormal><SPAN style="FONT-FAMILY: NSimSun; FONT-SIZE: 9.5pt; mso-bidi-font-family: NSimSun"><SPAN style="mso-spacerun: yes">&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp; </SPAN>{<o:p></o:p></SPAN></P>
<P style="LINE-HEIGHT: normal; MARGIN: 0in 0in 0pt; mso-layout-grid-align: none" class=MsoNormal><SPAN style="FONT-FAMILY: NSimSun; FONT-SIZE: 9.5pt; mso-bidi-font-family: NSimSun"><SPAN style="mso-spacerun: yes">&nbsp;&nbsp; </SPAN><SPAN style="mso-spacerun: yes">&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;</SPAN><SPAN style="COLOR: green">//access data in the implementation variable</SPAN><o:p></o:p></SPAN></P>
<P style="LINE-HEIGHT: normal; MARGIN: 0in 0in 0pt; mso-layout-grid-align: none" class=MsoNormal><SPAN style="FONT-FAMILY: NSimSun; FONT-SIZE: 9.5pt; mso-bidi-font-family: NSimSun"><SPAN style="mso-spacerun: yes">&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp; </SPAN><SPAN style="COLOR: blue">int</SPAN> nextChildIndex = <SPAN style="COLOR: blue">this</SPAN>.index.Get(context);<o:p></o:p></SPAN></P>
<P style="LINE-HEIGHT: normal; MARGIN: 0in 0in 0pt; mso-layout-grid-align: none" class=MsoNormal><SPAN style="FONT-FAMILY: NSimSun; FONT-SIZE: 9.5pt; mso-bidi-font-family: NSimSun"><SPAN style="mso-spacerun: yes">&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp; </SPAN><SPAN style="COLOR: blue">if</SPAN> (nextChildIndex &lt; <SPAN style="COLOR: blue">this</SPAN>.Activities.Count)<o:p></o:p></SPAN></P>
<P style="LINE-HEIGHT: normal; MARGIN: 0in 0in 0pt; mso-layout-grid-align: none" class=MsoNormal><SPAN style="FONT-FAMILY: NSimSun; FONT-SIZE: 9.5pt; mso-bidi-font-family: NSimSun"><SPAN style="mso-spacerun: yes">&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp; </SPAN>{<o:p></o:p></SPAN></P>
<P style="LINE-HEIGHT: normal; MARGIN: 0in 0in 0pt; mso-layout-grid-align: none" class=MsoNormal><SPAN style="FONT-FAMILY: NSimSun; FONT-SIZE: 9.5pt; mso-bidi-font-family: NSimSun"><SPAN style="mso-spacerun: yes">&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp; </SPAN>context.ScheduleActivity(<SPAN style="COLOR: blue">this</SPAN>.Activities[nextChildIndex], onChildCompleted);<o:p></o:p></SPAN></P>
<P style="LINE-HEIGHT: normal; MARGIN: 0in 0in 0pt; mso-layout-grid-align: none" class=MsoNormal><SPAN style="FONT-FAMILY: NSimSun; FONT-SIZE: 9.5pt; mso-bidi-font-family: NSimSun"><SPAN style="mso-spacerun: yes">&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp; </SPAN><SPAN style="COLOR: blue">this</SPAN>.index.Set(context, nextChildIndex + 1);<o:p></o:p></SPAN></P>
<P style="LINE-HEIGHT: normal; MARGIN: 0in 0in 0pt; mso-layout-grid-align: none" class=MsoNormal><SPAN style="FONT-FAMILY: NSimSun; FONT-SIZE: 9.5pt; mso-bidi-font-family: NSimSun"><SPAN style="mso-spacerun: yes">&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp; </SPAN>}<o:p></o:p></SPAN></P>
<P style="LINE-HEIGHT: normal; MARGIN: 0in 0in 0pt; mso-layout-grid-align: none" class=MsoNormal><SPAN style="FONT-FAMILY: NSimSun; FONT-SIZE: 9.5pt; mso-bidi-font-family: NSimSun"><SPAN style="mso-spacerun: yes">&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp; </SPAN>}<o:p></o:p></SPAN></P>
<P style="LINE-HEIGHT: normal; MARGIN: 0in 0in 0pt; mso-layout-grid-align: none" class=MsoNormal><SPAN style="FONT-FAMILY: NSimSun; FONT-SIZE: 9.5pt; mso-bidi-font-family: NSimSun"><o:p>&nbsp;</o:p></SPAN></P>
<P style="LINE-HEIGHT: normal; MARGIN: 0in 0in 0pt; mso-layout-grid-align: none" class=MsoNormal><SPAN style="FONT-FAMILY: NSimSun; FONT-SIZE: 9.5pt; mso-bidi-font-family: NSimSun"><SPAN style="mso-spacerun: yes">&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp; </SPAN><SPAN style="COLOR: blue">void</SPAN> onChildCompleted(<SPAN style="COLOR: #2b91af">NativeActivityContext</SPAN> context, <SPAN style="COLOR: #2b91af">ActivityInstance</SPAN> instance)<o:p></o:p></SPAN></P>
<P style="LINE-HEIGHT: normal; MARGIN: 0in 0in 0pt; mso-layout-grid-align: none" class=MsoNormal><SPAN style="FONT-FAMILY: NSimSun; FONT-SIZE: 9.5pt; mso-bidi-font-family: NSimSun"><SPAN style="mso-spacerun: yes">&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp; </SPAN>{<o:p></o:p></SPAN></P>
<P style="LINE-HEIGHT: normal; MARGIN: 0in 0in 0pt; mso-layout-grid-align: none" class=MsoNormal><SPAN style="FONT-FAMILY: NSimSun; FONT-SIZE: 9.5pt; mso-bidi-font-family: NSimSun"><SPAN style="mso-spacerun: yes">&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp; </SPAN>ScheduleNextChild(context);<o:p></o:p></SPAN></P>
<P style="LINE-HEIGHT: normal; MARGIN: 0in 0in 0pt; mso-layout-grid-align: none" class=MsoNormal><SPAN style="FONT-FAMILY: NSimSun; FONT-SIZE: 9.5pt; mso-bidi-font-family: NSimSun"><SPAN style="mso-spacerun: yes">&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp; </SPAN>}<o:p></o:p></SPAN></P>
<P style="LINE-HEIGHT: normal; MARGIN: 0in 0in 0pt; mso-layout-grid-align: none" class=MsoNormal><SPAN style="FONT-FAMILY: NSimSun; FONT-SIZE: 9.5pt; mso-bidi-font-family: NSimSun"><SPAN style="mso-spacerun: yes">&nbsp;&nbsp;&nbsp; </SPAN>}<o:p></o:p></SPAN></P>
<P style="MARGIN: 0in 0in 10pt" class=MsoCaption><STRONG><FONT color=#4f81bd><FONT face=Calibri><SPAN style="mso-spacerun: yes">&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp; </SPAN>Code <SPAN style="mso-no-proof: yes">20. A simple implementation of Sequence Activity with both public and implementation variables.</SPAN></FONT></FONT></STRONG></P>
<P style="MARGIN: 0in 0in 10pt" class=MsoNormal><FONT size=3><FONT face=Calibri>This Activity has a collection of variables for its users to fill and it declare it as public by using “metadata.AddVariable” in CacheMetadata method; it also has a variable to keep track of execution progression, it’s never exposed to the Activity’s users and is declared as implementation by using “metadata.AddImplementationVariable”.<o:p></o:p></FONT></FONT></P>
<P style="MARGIN: 0in 0in 10pt" class=MsoNormal><FONT size=3><FONT face=Calibri>Note that, if base.CacheMatadata is called in CacheMetadata method, the 2 foreach loops are not necessary anymore. Because the base implementation of CacheMetadata reflects all the public properties of the Activity, and automatically declare any public Activity, including Activity in public collections, as its public child; it does similar thing for variables.<o:p></o:p></FONT></FONT></P>
<H1 style="MARGIN: 24pt 0in 0pt"><FONT size=5><FONT color=#365f91><FONT face=Cambria>Data scoping<o:p></o:p></FONT></FONT></FONT></H1>
<P style="MARGIN: 0in 0in 10pt" class=MsoNormal><FONT face=Calibri><FONT size=3>With “public” and “implementation” defined, it’s easier to define scoping. In WF4, variables and arguments are all scoped with those rules:<o:p></o:p></FONT></FONT></P>
<P style="TEXT-INDENT: -0.25in; MARGIN: 0in 0in 0pt 0.5in; mso-list: l0 level1 lfo1" class=MsoListParagraphCxSpFirst><SPAN style="FONT-FAMILY: Symbol; mso-fareast-font-family: Symbol; mso-bidi-font-family: Symbol"><SPAN style="mso-list: Ignore"><FONT size=3>·</FONT><SPAN style="FONT: 7pt 'Times New Roman'">&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp; </SPAN></SPAN></SPAN><FONT face=Calibri><FONT size=3>An Activity’s arguments and implementation variables could only be accessed by its implementation child Activities<o:p></o:p></FONT></FONT></P>
<P style="TEXT-INDENT: -0.25in; MARGIN: 0in 0in 10pt 0.5in; mso-list: l0 level1 lfo1" class=MsoListParagraphCxSpLast><SPAN style="FONT-FAMILY: Symbol; mso-fareast-font-family: Symbol; mso-bidi-font-family: Symbol"><SPAN style="mso-list: Ignore"><FONT size=3>·</FONT><SPAN style="FONT: 7pt 'Times New Roman'">&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp; </SPAN></SPAN></SPAN><FONT size=3><FONT face=Calibri>An Activity’s public variables could only be accessed by its public child Activities<o:p></o:p></FONT></FONT></P>
<P style="MARGIN: 0in 0in 10pt" class=MsoNormal><FONT size=3><FONT face=Calibri>Hopefully those rules are pretty clear after the explanation in the previous section. <o:p></o:p></FONT></FONT></P>
<P mce_keep="true">Yun Jin <BR>Development Lead <BR><A href="http://blogs.msdn.com/yunjin"><STRONG><FONT color=#006bad>http://blogs.msdn.com/yunjin</FONT></STRONG></A></P>]]></content:encoded>
    </item>
    <item>
      <title>WF State Machine Activity Pack CTP1 Released</title>
      <link>https://docs.microsoft.com/archive/blogs/flow/wf-state-machine-activity-pack-ctp1-released</link>
      <pubDate>Wed, 21 Apr 2010 01:58:00 GMT</pubDate>
      <dc:creator><![CDATA[alanko]]></dc:creator>
      <guid
        isPermaLink="false">https://blogs.msdn.microsoft.com/flow/2010/04/21/wf-state-machine-activity-pack-ctp1-released/</guid>
      <description><![CDATA[The WF&nbsp;State Machine Activity Pack CTP1 is released on CodePlex NOW!!&nbsp; Please check it...]]></description>
      <content:encoded><![CDATA[<P><A href="http://wf.codeplex.com/releases/view/43586" mce_href="http://wf.codeplex.com/releases/view/43586">The WF&nbsp;State Machine Activity Pack CTP1</A> is released on <A href="http://wf.codeplex.com/" mce_href="http://wf.codeplex.com/">CodePlex</A> NOW!!&nbsp; Please check it out.</P>
<P>Last year in PDC2009, I ran a <A href="http://blogs.msdn.com/flow/archive/2009/12/09/chalk-talk-in-pdc09-future-directions-for-state-machine-workflows.aspx" mce_href="http://blogs.msdn.com/flow/archive/2009/12/09/chalk-talk-in-pdc09-future-directions-for-state-machine-workflows.aspx">chalk talk</A> on our work on WF 4 State Machine Activities and promised the team would ship an implementation for public review after the release of <A href="http://www.microsoft.com/visualstudio" mce_href="http://www.microsoft.com/visualstudio">Visual Studio 2010</A>.&nbsp; Today, I am so excited to let you know that we have delivered it on CodePlex as planned.</P>
<P>This CTP contains a state machine runtime and a graphical state machine designer implementation, and they are optimized to handle event-driven scenarios.&nbsp;&nbsp; We simplified the runtime object model and enhanced the designer experience so that handling transitions among states should be more intuitive and require fewer clicks or drag-and-drops comparing to WF3.&nbsp;<SPAN style="LINE-HEIGHT: 115%; FONT-FAMILY: 'Calibri','sans-serif'; FONT-SIZE: 11pt; mso-bidi-font-family: 'Times New Roman'; mso-fareast-font-family: SimSun; mso-ascii-theme-font: minor-latin; mso-hansi-theme-font: minor-latin; mso-fareast-theme-font: minor-fareast; mso-bidi-theme-font: minor-bidi; mso-ansi-language: EN-US; mso-fareast-language: ZH-CN; mso-bidi-language: AR-SA">In WF 4, we have also introduced the Flowchart modeling style. State Machine and Flowchart styles are highly complementary. They are suitable for different scenarios. We will talk more about&nbsp;that in future blogs.</SPAN> </P>
<P>So, go ahead to <A href="http://wf.codeplex.com/releases/view/43586#DownloadId=116930" mce_href="http://wf.codeplex.com/releases/view/43586#DownloadId=116930">download and install the bits</A>. The <A href="http://wf.codeplex.com/releases/view/43586#DownloadId=117204" mce_href="http://wf.codeplex.com/releases/view/43586#DownloadId=117204">user guide</A> is a good starting point.&nbsp; <SPAN style="LINE-HEIGHT: 115%; FONT-FAMILY: 'Calibri','sans-serif'; FONT-SIZE: 11pt; mso-bidi-font-family: 'Times New Roman'; mso-fareast-font-family: SimSun; mso-ascii-theme-font: minor-latin; mso-hansi-theme-font: minor-latin; mso-fareast-theme-font: minor-fareast; mso-bidi-theme-font: minor-bidi; mso-ansi-language: EN-US; mso-fareast-language: ZH-CN; mso-bidi-language: AR-SA">If you are interested in how it is implemented, you can download the <A href="http://wf.codeplex.com/releases/view/43586#DownloadId=117205"><FONT color=#0000ff>source code</FONT></A>. </SPAN>For WF 3 users, you can find the comparison between the state machine in WF3 and this CTP in the user guide.&nbsp; And the team will continue to blog about different features such as composite states, conditional transition, etc…&nbsp; </P>
<P>Your feedback is important to us.&nbsp; We would like to understand more about your State Machine scenarios to build the State Machine right for your business needs.&nbsp; So, please be encouraged to validate the implementation with your scenarios and let us know how it fits or doesn’t fit your scenarios.</P>
<P><A href="https://msdnshared.blob.core.windows.net/media/TNBlogsFS/BlogFileStorage/blogs_msdn/flow/WindowsLiveWriter/WFStateMachineActivityPackCTP1Released_A3DB/state%20machine_2.jpg" original-url="http://blogs.msdn.com/blogfiles/flow/WindowsLiveWriter/WFStateMachineActivityPackCTP1Released_A3DB/state%20machine_2.jpg" mce_href="http://blogs.msdn.com/blogfiles/flow/WindowsLiveWriter/WFStateMachineActivityPackCTP1Released_A3DB/state%20machine_2.jpg"><IMG style="BORDER-RIGHT-WIDTH: 0px; DISPLAY: inline; BORDER-TOP-WIDTH: 0px; BORDER-BOTTOM-WIDTH: 0px; BORDER-LEFT-WIDTH: 0px" title="state machine" border=0 alt="state machine" src="https://msdnshared.blob.core.windows.net/media/TNBlogsFS/BlogFileStorage/blogs_msdn/flow/WindowsLiveWriter/WFStateMachineActivityPackCTP1Released_A3DB/state%20machine_thumb.jpg" original-url="http://blogs.msdn.com/blogfiles/flow/WindowsLiveWriter/WFStateMachineActivityPackCTP1Released_A3DB/state%20machine_thumb.jpg" width=401 height=252 mce_src="http://blogs.msdn.com/blogfiles/flow/WindowsLiveWriter/WFStateMachineActivityPackCTP1Released_A3DB/state%20machine_thumb.jpg"></A> </P>
<P>Alan Ko (<A href="mailto:alanko@microsoft.com" mce_href="mailto:alanko@microsoft.com">alanko@microsoft.com</A>)</P>
<P>Program Manager (The WF team)</P>]]></content:encoded>
    </item>
    <item>
      <title>WF ADO.NET Activity Pack CTP1 Released</title>
      <link>https://docs.microsoft.com/archive/blogs/flow/wf-ado-net-activity-pack-ctp1-released</link>
      <pubDate>Wed, 21 Apr 2010 01:36:00 GMT</pubDate>
      <dc:creator><![CDATA[alanko]]></dc:creator>
      <guid
        isPermaLink="false">https://blogs.msdn.microsoft.com/flow/2010/04/21/wf-ado-net-activity-pack-ctp1-released/</guid>
      <description><![CDATA[We are happy to announce that we have released the WF ADO.NET Activity Pack CTP1 on CodePlex. 
The...]]></description>
      <content:encoded><![CDATA[<P mce_keep="true">We are happy to announce that we have released <A href="http://wf.codeplex.com/releases/view/43585" mce_href="http://wf.codeplex.com/releases/view/43585">the WF ADO.NET Activity Pack CTP1</A> on <A href="http://wf.codeplex.com/" mce_href="http://wf.codeplex.com/">CodePlex</A>. </P>
<P>The WF ADO.NET Activity Pack CTP1&nbsp;contains a set of WF 4 Activities based on <A href="http://msdn.microsoft.com/en-us/library/s7ee2dwt(VS.71).aspx" mce_href="http://msdn.microsoft.com/en-us/library/s7ee2dwt(VS.71).aspx">.NET Framework Data Providers</A>. These activities enable accessing a database through SQL commands or stored procedures within a workflow.&nbsp; You can drag-and-drop the ADO.NET Activities to your designer surface and access the database just like what you can do with ADO.NET. <SPAN style="LINE-HEIGHT: 115%; FONT-FAMILY: 'Calibri','sans-serif'; FONT-SIZE: 11pt; mso-bidi-font-family: 'Times New Roman'; mso-fareast-font-family: SimSun; mso-ascii-theme-font: minor-latin; mso-hansi-theme-font: minor-latin; mso-fareast-theme-font: minor-fareast; mso-bidi-theme-font: minor-bidi; mso-ansi-language: EN-US; mso-fareast-language: ZH-CN; mso-bidi-language: AR-SA">It is a very simple way for you to integrate business data into your workflows.</SPAN></P>
<P>Click here to <A href="http://wf.codeplex.com/releases/view/43585#DownloadId=116931" mce_href="http://wf.codeplex.com/releases/view/43585#DownloadId=116931">download and install the bits</A>, the <A href="http://wf.codeplex.com/releases/view/43585#DownloadId=117206" mce_href="http://wf.codeplex.com/releases/view/43585#DownloadId=117206">user guide</A>, and the <A href="http://wf.codeplex.com/releases/view/43585#DownloadId=117208" mce_href="http://wf.codeplex.com/releases/view/43585#DownloadId=117208">source code</A>.</P>
<P>The Microsoft WF Team</P>]]></content:encoded>
    </item>
    <item>
      <title>Workflow Foundation 4.0 Activity Data Model (II)</title>
      <link>https://docs.microsoft.com/archive/blogs/flow/workflow-foundation-4-0-activity-data-model-ii</link>
      <pubDate>Tue, 06 Apr 2010 07:28:00 GMT</pubDate>
      <dc:creator><![CDATA[Yun Jin]]></dc:creator>
      <guid
        isPermaLink="false">https://blogs.msdn.microsoft.com/flow/2010/04/06/workflow-foundation-4-0-activity-data-model-ii/</guid>
      <description><![CDATA[In the 1st segment, I talked about high level principle for WF4’s data model design. I’m going to...]]></description>
      <content:encoded><![CDATA[<P>In the <A title="Workflow Activity Data Model" href="http://blogs.msdn.com/flow/archive/2010/04/05/workflow-foundation-4-0-activity-data-model-i.aspx" mce_href="http://blogs.msdn.com/flow/archive/2010/04/05/workflow-foundation-4-0-activity-data-model-i.aspx"><STRONG><FONT color=#006bad>1st segment</FONT></STRONG></A>, I talked about high level principle for WF4’s data model design. I’m going to talk about WF Argument in particular in this post.<FONT size=5><FONT color=#365f91><FONT face=Cambria></P></FONT></FONT></FONT>
<P style="MARGIN: 0in 0in 10pt" class=MsoNormal><FONT size=3><FONT face=Calibri></FONT></FONT></P>
<H1 style="MARGIN: 24pt 0in 0pt"><FONT size=5><FONT color=#365f91><FONT face=Cambria>Argument<?xml:namespace prefix = o ns = "urn:schemas-microsoft-com:office:office" /><o:p></o:p></FONT></FONT></FONT></H1>
<P style="MARGIN: 0in 0in 10pt" class=MsoNormal><FONT size=3><FONT face=Calibri>We’ve briefly touched this before: in WF4, arguments are modeled by Argument class.<o:p></o:p></FONT></FONT></P>
<P style="LINE-HEIGHT: normal; TEXT-INDENT: 0.5in; MARGIN: 0in 0in 0pt; mso-layout-grid-align: none" class=MsoNormal><SPAN style="FONT-FAMILY: NSimSun; COLOR: blue; FONT-SIZE: 9pt; mso-bidi-font-family: NSimSun">namespace</SPAN><SPAN style="FONT-FAMILY: NSimSun; FONT-SIZE: 9pt; mso-bidi-font-family: NSimSun"> System.Activities<o:p></o:p></SPAN></P>
<P style="LINE-HEIGHT: normal; MARGIN: 0in 0in 0pt 0.5in; mso-layout-grid-align: none" class=MsoNormal><SPAN style="FONT-FAMILY: NSimSun; FONT-SIZE: 9pt; mso-bidi-font-family: NSimSun">{<SPAN style="COLOR: blue"><SPAN style="mso-spacerun: yes">&nbsp;&nbsp; </SPAN><o:p></o:p></SPAN></SPAN></P>
<P style="LINE-HEIGHT: normal; TEXT-INDENT: 0.25in; MARGIN: 0in 0in 0pt 0.5in; mso-layout-grid-align: none" class=MsoNormal><SPAN style="FONT-FAMILY: NSimSun; COLOR: blue; FONT-SIZE: 9pt; mso-bidi-font-family: NSimSun">public</SPAN><SPAN style="FONT-FAMILY: NSimSun; FONT-SIZE: 9pt; mso-bidi-font-family: NSimSun"> <SPAN style="COLOR: blue">abstract</SPAN> <SPAN style="COLOR: blue">class</SPAN> <SPAN style="COLOR: #2b91af">Argument</SPAN><o:p></o:p></SPAN></P>
<P style="LINE-HEIGHT: normal; TEXT-INDENT: 0.25in; MARGIN: 0in 0in 0pt 0.5in; mso-layout-grid-align: none" class=MsoNormal><SPAN style="FONT-FAMILY: NSimSun; FONT-SIZE: 9pt; mso-bidi-font-family: NSimSun">{<o:p></o:p></SPAN></P>
<P style="LINE-HEIGHT: normal; TEXT-INDENT: 0.25in; MARGIN: 0in 0in 0pt 0.5in; mso-layout-grid-align: none" class=MsoNormal><SPAN style="FONT-FAMILY: NSimSun; FONT-SIZE: 9pt; mso-bidi-font-family: NSimSun"><SPAN style="mso-spacerun: yes">&nbsp;&nbsp;&nbsp; </SPAN><SPAN style="COLOR: blue">public</SPAN> <SPAN style="COLOR: #2b91af">Type</SPAN> ArgumentType { <SPAN style="COLOR: blue">get</SPAN>; <SPAN style="COLOR: blue">internal</SPAN> <SPAN style="COLOR: blue">set</SPAN>; }<SPAN style="mso-spacerun: yes">&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp; </SPAN><o:p></o:p></SPAN></P>
<P style="LINE-HEIGHT: normal; MARGIN: 0in 0in 0pt 0.5in; mso-layout-grid-align: none" class=MsoNormal><SPAN style="FONT-FAMILY: NSimSun; FONT-SIZE: 9pt; mso-bidi-font-family: NSimSun"><SPAN style="mso-spacerun: yes">&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp; </SPAN><SPAN style="COLOR: blue">public</SPAN> <SPAN style="COLOR: #2b91af">ArgumentDirection</SPAN> Direction { <SPAN style="COLOR: blue">get</SPAN>; <SPAN style="COLOR: blue">internal</SPAN> <SPAN style="COLOR: blue">set</SPAN>; }<SPAN style="mso-spacerun: yes">&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp; </SPAN><SPAN style="COLOR: blue"><o:p></o:p></SPAN></SPAN></P>
<P style="LINE-HEIGHT: normal; TEXT-INDENT: 0.5in; MARGIN: 0in 0in 0pt 0.5in; mso-layout-grid-align: none" class=MsoNormal><SPAN style="FONT-FAMILY: NSimSun; COLOR: blue; FONT-SIZE: 9pt; mso-bidi-font-family: NSimSun">public</SPAN><SPAN style="FONT-FAMILY: NSimSun; FONT-SIZE: 9pt; mso-bidi-font-family: NSimSun"> <SPAN style="COLOR: #2b91af">ActivityWithResult</SPAN> Expression { <SPAN style="COLOR: blue">get</SPAN>; <SPAN style="COLOR: blue">set</SPAN>; }<SPAN style="COLOR: blue"><o:p></o:p></SPAN></SPAN></P>
<P style="LINE-HEIGHT: normal; TEXT-INDENT: 0.5in; MARGIN: 0in 0in 0pt 0.5in; mso-layout-grid-align: none" class=MsoNormal><SPAN style="FONT-FAMILY: NSimSun; FONT-SIZE: 9pt; mso-bidi-font-family: NSimSun">…<o:p></o:p></SPAN></P>
<P style="LINE-HEIGHT: normal; MARGIN: 0in 0in 0pt 0.5in; mso-layout-grid-align: none" class=MsoNormal><SPAN style="FONT-FAMILY: NSimSun; FONT-SIZE: 9pt; mso-bidi-font-family: NSimSun"><SPAN style="mso-spacerun: yes">&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp; </SPAN><SPAN style="COLOR: blue">public</SPAN> <SPAN style="COLOR: blue">object</SPAN> Get(<SPAN style="COLOR: #2b91af">ActivityContext</SPAN> context);<o:p></o:p></SPAN></P>
<P style="LINE-HEIGHT: normal; MARGIN: 0in 0in 0pt 0.5in; mso-layout-grid-align: none" class=MsoNormal><SPAN style="FONT-FAMILY: NSimSun; FONT-SIZE: 9pt; mso-bidi-font-family: NSimSun"><SPAN style="mso-spacerun: yes">&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp; </SPAN><SPAN style="COLOR: blue">public</SPAN> <SPAN style="COLOR: blue">void</SPAN> Set(<SPAN style="COLOR: #2b91af">ActivityContext</SPAN> context, <SPAN style="COLOR: blue">object</SPAN> value);<o:p></o:p></SPAN></P>
<P style="LINE-HEIGHT: normal; MARGIN: 0in 0in 0pt 0.5in; mso-layout-grid-align: none" class=MsoNormal><SPAN style="FONT-FAMILY: NSimSun; FONT-SIZE: 9pt; mso-bidi-font-family: NSimSun"><SPAN style="mso-tab-count: 1">&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp; </SPAN>…<o:p></o:p></SPAN></P>
<P style="LINE-HEIGHT: normal; TEXT-INDENT: 0.25in; MARGIN: 0in 0in 0pt 0.5in; mso-layout-grid-align: none" class=MsoNormal><SPAN style="FONT-FAMILY: NSimSun; FONT-SIZE: 9pt; mso-bidi-font-family: NSimSun">}<o:p></o:p></SPAN></P>
<P style="LINE-HEIGHT: normal; TEXT-INDENT: 0.5in; MARGIN: 0in 0in 0pt; mso-layout-grid-align: none" class=MsoNormal><SPAN style="FONT-FAMILY: NSimSun; FONT-SIZE: 9pt; mso-bidi-font-family: NSimSun">}<o:p></o:p></SPAN></P>
<P style="MARGIN: 0in 0in 10pt" class=MsoCaption><STRONG><FONT color=#4f81bd><FONT face=Calibri><SPAN style="mso-spacerun: yes">&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp; </SPAN><SPAN style="mso-spacerun: yes">&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;</SPAN><SPAN style="mso-spacerun: yes">&nbsp;</SPAN>Code <SPAN style="mso-no-proof: yes">5</SPAN>. Argument class definition<o:p></o:p></FONT></FONT></STRONG></P>
<P style="MARGIN: 0in 0in 10pt" class=MsoNormal><FONT size=3><FONT face=Calibri>This class has some pretty straightforward properties you’d expect to define an argument like ArgumentType and Direction (In, Out, InOut). Expression is a formula given by Activity caller to tell WF runtime how to evaluate an Argument’s value at execution time, which we will discuss in details later. The most important methods on Argument is Get() and Set(). Get() is to fetch runtime value of an input argument from ActivityContext; similarly, Set() is used to set runtime value of an output argument to ActivityContext. <o:p></o:p></FONT></FONT></P>
<P mce_keep="true"><SPAN style="LINE-HEIGHT: 115%; FONT-FAMILY: 'Calibri','sans-serif'; FONT-SIZE: 11pt; mso-bidi-font-family: 'Times New Roman'; mso-fareast-font-family: 宋体; mso-ascii-theme-font: minor-latin; mso-hansi-theme-font: minor-latin; mso-fareast-theme-font: minor-fareast; mso-bidi-theme-font: minor-bidi; mso-ansi-language: EN-US; mso-fareast-language: ZH-CN; mso-bidi-language: AR-SA">Look closely, you will find Argument is just an abstract class, so you could not instantiate this class directly. All it does is to provide a common interface for different type of arguments. This is the class diagram for Argument type tree:</SPAN>&nbsp;</P>
<P mce_keep="true">&nbsp;</P>
<P style="MARGIN: 0in 0in 10pt" class=MsoCaption><A href="https://msdnshared.blob.core.windows.net/media/TNBlogsFS/BlogFileStorage/blogs_msdn/flow/WindowsLiveWriter/WorkflowFoundation4.0ActivityDataModelII_13EA2/image_2.png" original-url="http://blogs.msdn.com/blogfiles/flow/WindowsLiveWriter/WorkflowFoundation4.0ActivityDataModelII_13EA2/image_2.png"><IMG style="BORDER-RIGHT-WIDTH: 0px; DISPLAY: inline; BORDER-TOP-WIDTH: 0px; BORDER-BOTTOM-WIDTH: 0px; BORDER-LEFT-WIDTH: 0px" title=image border=0 alt=image src="https://msdnshared.blob.core.windows.net/media/TNBlogsFS/BlogFileStorage/blogs_msdn/flow/WindowsLiveWriter/WorkflowFoundation4.0ActivityDataModelII_13EA2/image_thumb.png" original-url="http://blogs.msdn.com/blogfiles/flow/WindowsLiveWriter/WorkflowFoundation4.0ActivityDataModelII_13EA2/image_thumb.png" width=435 height=243></A> </P>
<P style="MARGIN: 0in 0in 10pt" class=MsoCaption><STRONG><FONT color=#4f81bd><FONT face=Calibri>Figure <SPAN style="mso-no-proof: yes">1</SPAN>. Argument class hierarchy </FONT></P></FONT></STRONG>
<P style="MARGIN: 0in 0in 10pt" class=MsoNormal><FONT size=3><FONT face=Calibri>In the tree, there are 3 more abstract classes with predefined ArgumentDirection: InArgument, OutArgument, and InOutArgument. And then there are 3 concrete classes which allow user to specify ArgumentType using generic type parameter: InArgument&lt;T&gt;, OutArgument&lt;T&gt;, and InOutArgument&lt;T&gt;. Eventually users of an Activity need to assign an argument to instance of one of those classes.<o:p></o:p></FONT></FONT></P>
<H2 style="MARGIN: auto 0in"><SPAN style="FONT-FAMILY: 'Cambria','serif'; COLOR: #365f91; FONT-SIZE: 12pt; mso-bidi-font-family: 'Times New Roman'; mso-fareast-font-family: 宋体; mso-ascii-theme-font: major-latin; mso-hansi-theme-font: major-latin; mso-fareast-theme-font: major-fareast; mso-bidi-theme-font: major-bidi; mso-themecolor: accent1; mso-themeshade: 191">Argument declaration<o:p></o:p></SPAN></H2>
<P style="MARGIN: 0in 0in 10pt" class=MsoNormal><FONT size=3><FONT face=Calibri>In C#, developers enclose arguments in a pair of parentheses after method name to “declare” those arguments to C# compiler. In WF, an Activity tree is executed by WF runtime, how would the runtime knows which Activity has defined what arguments?<SPAN style="mso-spacerun: yes">&nbsp;&nbsp; </SPAN>The answer is that Activity class needs to report its metadata, including arguments and variables, to the runtime using a virtual method CacheMetadata. Here is an example about how this method could be used to declare an argument:<o:p></o:p></FONT></FONT></P>
<P style="LINE-HEIGHT: normal; MARGIN: 0in 0in 0pt; mso-layout-grid-align: none" class=MsoNormal><SPAN style="FONT-FAMILY: NSimSun; COLOR: blue; FONT-SIZE: 9pt; mso-bidi-font-family: NSimSun"><SPAN style="mso-spacerun: yes">&nbsp;&nbsp;&nbsp; </SPAN>public</SPAN><SPAN style="FONT-FAMILY: NSimSun; FONT-SIZE: 9pt; mso-bidi-font-family: NSimSun"> <SPAN style="COLOR: blue">class</SPAN> <SPAN style="COLOR: #2b91af">MyWriteLine</SPAN> : <SPAN style="COLOR: #2b91af">CodeActivity</SPAN><o:p></o:p></SPAN></P>
<P style="LINE-HEIGHT: normal; MARGIN: 0in 0in 0pt; mso-layout-grid-align: none" class=MsoNormal><SPAN style="FONT-FAMILY: NSimSun; FONT-SIZE: 9pt; mso-bidi-font-family: NSimSun"><SPAN style="mso-spacerun: yes">&nbsp;&nbsp;&nbsp; </SPAN>{<o:p></o:p></SPAN></P>
<P style="LINE-HEIGHT: normal; MARGIN: 0in 0in 0pt; mso-layout-grid-align: none" class=MsoNormal><SPAN style="FONT-FAMILY: NSimSun; FONT-SIZE: 9pt; mso-bidi-font-family: NSimSun"><SPAN style="mso-spacerun: yes">&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp; </SPAN><SPAN style="COLOR: blue">public</SPAN> <SPAN style="COLOR: #2b91af">InArgument</SPAN>&lt;<SPAN style="COLOR: blue">string</SPAN>&gt; Text<o:p></o:p></SPAN></P>
<P style="LINE-HEIGHT: normal; MARGIN: 0in 0in 0pt; mso-layout-grid-align: none" class=MsoNormal><SPAN style="FONT-FAMILY: NSimSun; FONT-SIZE: 9pt; mso-bidi-font-family: NSimSun"><SPAN style="mso-spacerun: yes">&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp; </SPAN>{<o:p></o:p></SPAN></P>
<P style="LINE-HEIGHT: normal; MARGIN: 0in 0in 0pt; mso-layout-grid-align: none" class=MsoNormal><SPAN style="FONT-FAMILY: NSimSun; FONT-SIZE: 9pt; mso-bidi-font-family: NSimSun"><SPAN style="mso-spacerun: yes">&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp; </SPAN><SPAN style="COLOR: blue">get</SPAN>;<o:p></o:p></SPAN></P>
<P style="LINE-HEIGHT: normal; MARGIN: 0in 0in 0pt; mso-layout-grid-align: none" class=MsoNormal><SPAN style="FONT-FAMILY: NSimSun; FONT-SIZE: 9pt; mso-bidi-font-family: NSimSun"><SPAN style="mso-spacerun: yes">&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp; </SPAN><SPAN style="COLOR: blue">set</SPAN>;<o:p></o:p></SPAN></P>
<P style="LINE-HEIGHT: normal; MARGIN: 0in 0in 0pt; mso-layout-grid-align: none" class=MsoNormal><SPAN style="FONT-FAMILY: NSimSun; FONT-SIZE: 9pt; mso-bidi-font-family: NSimSun"><SPAN style="mso-spacerun: yes">&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp; </SPAN>}<o:p></o:p></SPAN></P>
<P style="LINE-HEIGHT: normal; MARGIN: 0in 0in 0pt; mso-layout-grid-align: none" class=MsoNormal><SPAN style="FONT-FAMILY: NSimSun; FONT-SIZE: 9pt; mso-bidi-font-family: NSimSun"><o:p>&nbsp;</o:p></SPAN></P>
<P style="LINE-HEIGHT: normal; MARGIN: 0in 0in 0pt; mso-layout-grid-align: none" class=MsoNormal><SPAN style="FONT-FAMILY: NSimSun; FONT-SIZE: 9pt; mso-bidi-font-family: NSimSun"><SPAN style="mso-spacerun: yes">&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp; </SPAN><SPAN style="COLOR: blue">protected</SPAN> <SPAN style="COLOR: blue">override</SPAN> <SPAN style="COLOR: blue">void</SPAN> CacheMetadata(<SPAN style="COLOR: #2b91af">CodeActivityMetadata</SPAN> metadata)<o:p></o:p></SPAN></P>
<P style="LINE-HEIGHT: normal; MARGIN: 0in 0in 0pt; mso-layout-grid-align: none" class=MsoNormal><SPAN style="FONT-FAMILY: NSimSun; FONT-SIZE: 9pt; mso-bidi-font-family: NSimSun"><SPAN style="mso-spacerun: yes">&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp; </SPAN>{<o:p></o:p></SPAN></P>
<P style="LINE-HEIGHT: normal; MARGIN: 0in 0in 0pt; mso-layout-grid-align: none" class=MsoNormal><SPAN style="FONT-FAMILY: NSimSun; FONT-SIZE: 9pt; mso-bidi-font-family: NSimSun"><SPAN style="mso-spacerun: yes">&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp; </SPAN><SPAN style="COLOR: #2b91af">RuntimeArgument</SPAN> textArgument = <SPAN style="COLOR: blue">new</SPAN> <SPAN style="COLOR: #2b91af">RuntimeArgument</SPAN>(<SPAN style="COLOR: #a31515">"Text"</SPAN>, <SPAN style="COLOR: blue">typeof</SPAN>(<SPAN style="COLOR: blue">string</SPAN>), <SPAN style="COLOR: #2b91af">ArgumentDirection</SPAN>.In);<o:p></o:p></SPAN></P>
<P style="LINE-HEIGHT: normal; MARGIN: 0in 0in 0pt; mso-layout-grid-align: none" class=MsoNormal><SPAN style="FONT-FAMILY: NSimSun; FONT-SIZE: 9pt; mso-bidi-font-family: NSimSun"><SPAN style="mso-spacerun: yes">&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp; </SPAN>metadata.Bind(<SPAN style="COLOR: blue">this</SPAN>.Text, textArgument);<o:p></o:p></SPAN></P>
<P style="LINE-HEIGHT: normal; MARGIN: 0in 0in 0pt; mso-layout-grid-align: none" class=MsoNormal><SPAN style="FONT-FAMILY: NSimSun; FONT-SIZE: 9pt; mso-bidi-font-family: NSimSun"><SPAN style="mso-spacerun: yes">&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp; </SPAN>metadata.AddArgument(textArgument);<o:p></o:p></SPAN></P>
<P style="LINE-HEIGHT: normal; MARGIN: 0in 0in 0pt; mso-layout-grid-align: none" class=MsoNormal><SPAN style="FONT-FAMILY: NSimSun; FONT-SIZE: 9pt; mso-bidi-font-family: NSimSun"><SPAN style="mso-spacerun: yes">&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp; </SPAN>}<o:p></o:p></SPAN></P>
<P style="LINE-HEIGHT: normal; MARGIN: 0in 0in 0pt; mso-layout-grid-align: none" class=MsoNormal><SPAN style="FONT-FAMILY: NSimSun; FONT-SIZE: 9pt; mso-bidi-font-family: NSimSun"><SPAN style="mso-spacerun: yes">&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp; </SPAN>…<o:p></o:p></SPAN></P>
<P style="LINE-HEIGHT: normal; MARGIN: 0in 0in 0pt; mso-layout-grid-align: none" class=MsoNormal><SPAN style="FONT-FAMILY: NSimSun; FONT-SIZE: 9pt; mso-bidi-font-family: NSimSun"><SPAN style="mso-spacerun: yes">&nbsp;&nbsp;&nbsp; </SPAN>}<o:p></o:p></SPAN></P>
<P style="MARGIN: 0in 0in 10pt" class=MsoCaption><STRONG><FONT color=#4f81bd><FONT face=Calibri><SPAN style="mso-spacerun: yes">&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp; </SPAN>Code <SPAN style="mso-no-proof: yes">6</SPAN>. How to declare one argument on an Activity<o:p></o:p></FONT></FONT></STRONG></P>
<P style="MARGIN: 0in 0in 10pt" class=MsoNormal><FONT size=3><FONT face=Calibri>What WF runtime needs is really a RuntimeArgument object, the Argument object on Activity is only used to providing binding for the RuntimeArgument.<o:p></o:p></FONT></FONT></P>
<P style="MARGIN: 0in 0in 10pt" class=MsoNormal><FONT size=3><FONT face=Calibri>You may find interesting that MyWrite activity has worked before without overriding CacheMetadata method. The reason is that the method’s default implementation actually queries all public properties of an Activity using .Net reflection. For any property with type Argument, it automatically creates a RuntimeArgument with correct binding. So for most of common cases, an Activity would just work even without declaring arguments in CacheMetadata. However for developers who are sensitive to performance, it might be a good idea to override CacheMetadata to avoid cost of reflection.<o:p></o:p></FONT></FONT></P>
<P style="MARGIN: 0in 0in 10pt; WORD-BREAK: break-all; tab-stops: 45.8pt 91.6pt 137.4pt 183.2pt 229.0pt 274.8pt 320.6pt 366.4pt 412.2pt 458.0pt 503.8pt 549.6pt 595.4pt 641.2pt 687.0pt 732.8pt" class=MsoNormal><FONT size=3 face=Calibri>A common scenario where explicit argument declaration is required is dynamic argument: an Activity could take a list of arguments whose number and name are not predetermined by the Activity author. For example, if MyWriteLine wants to support formatted output similar to “Console.</FONT><SPAN style="LINE-HEIGHT: 115%; FONT-FAMILY: Consolas; COLOR: black; FONT-SIZE: 10pt; mso-fareast-font-family: 'Times New Roman'">WriteLine(</SPAN><SPAN style="LINE-HEIGHT: 115%; FONT-FAMILY: Consolas; COLOR: blue; FONT-SIZE: 10pt; mso-fareast-font-family: 'Times New Roman'">string</SPAN><SPAN style="LINE-HEIGHT: 115%; FONT-FAMILY: Consolas; COLOR: black; FONT-SIZE: 10pt; mso-fareast-font-family: 'Times New Roman'"> format,</SPAN><SPAN style="LINE-HEIGHT: 115%; FONT-FAMILY: Consolas; COLOR: blue; FONT-SIZE: 10pt; mso-fareast-font-family: 'Times New Roman'"> params</SPAN><SPAN style="LINE-HEIGHT: 115%; FONT-FAMILY: Consolas; COLOR: black; FONT-SIZE: 10pt; mso-fareast-font-family: 'Times New Roman'"> Object[] arg)</SPAN><FONT size=3><FONT face=Calibri>”, it needs to be written this way:<o:p></o:p></FONT></FONT></P>
<P style="LINE-HEIGHT: normal; MARGIN: 0in 0in 0pt; mso-layout-grid-align: none" class=MsoNormal><SPAN style="FONT-FAMILY: NSimSun; COLOR: blue; FONT-SIZE: 9pt; mso-bidi-font-family: NSimSun"><SPAN style="mso-spacerun: yes">&nbsp;&nbsp;&nbsp; </SPAN>public</SPAN><SPAN style="FONT-FAMILY: NSimSun; FONT-SIZE: 9pt; mso-bidi-font-family: NSimSun"> <SPAN style="COLOR: blue">class</SPAN> <SPAN style="COLOR: #2b91af">MyWriteLine</SPAN> : <SPAN style="COLOR: #2b91af">CodeActivity</SPAN><o:p></o:p></SPAN></P>
<P style="LINE-HEIGHT: normal; MARGIN: 0in 0in 0pt; mso-layout-grid-align: none" class=MsoNormal><SPAN style="FONT-FAMILY: NSimSun; FONT-SIZE: 9pt; mso-bidi-font-family: NSimSun"><SPAN style="mso-spacerun: yes">&nbsp;&nbsp;&nbsp; </SPAN>{<o:p></o:p></SPAN></P>
<P style="LINE-HEIGHT: normal; MARGIN: 0in 0in 0pt; mso-layout-grid-align: none" class=MsoNormal><SPAN style="FONT-FAMILY: NSimSun; FONT-SIZE: 9pt; mso-bidi-font-family: NSimSun"><SPAN style="mso-spacerun: yes">&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp; </SPAN><SPAN style="COLOR: #2b91af">Collection</SPAN>&lt;<SPAN style="COLOR: #2b91af">InArgument</SPAN>&gt; args = <SPAN style="COLOR: blue">new</SPAN> <SPAN style="COLOR: #2b91af">Collection</SPAN>&lt;<SPAN style="COLOR: #2b91af">InArgument</SPAN>&gt;();<o:p></o:p></SPAN></P>
<P style="LINE-HEIGHT: normal; MARGIN: 0in 0in 0pt; mso-layout-grid-align: none" class=MsoNormal><SPAN style="FONT-FAMILY: NSimSun; FONT-SIZE: 9pt; mso-bidi-font-family: NSimSun"><o:p>&nbsp;</o:p></SPAN></P>
<P style="LINE-HEIGHT: normal; MARGIN: 0in 0in 0pt; mso-layout-grid-align: none" class=MsoNormal><SPAN style="FONT-FAMILY: NSimSun; FONT-SIZE: 9pt; mso-bidi-font-family: NSimSun"><SPAN style="mso-spacerun: yes">&nbsp;</SPAN><SPAN style="mso-spacerun: yes">&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp; </SPAN><SPAN style="COLOR: blue">public</SPAN> <SPAN style="COLOR: #2b91af">InArgument</SPAN>&lt;<SPAN style="COLOR: blue">string</SPAN>&gt; Format<o:p></o:p></SPAN></P>
<P style="LINE-HEIGHT: normal; MARGIN: 0in 0in 0pt; mso-layout-grid-align: none" class=MsoNormal><SPAN style="FONT-FAMILY: NSimSun; FONT-SIZE: 9pt; mso-bidi-font-family: NSimSun"><SPAN style="mso-spacerun: yes">&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp; </SPAN>{<o:p></o:p></SPAN></P>
<P style="LINE-HEIGHT: normal; MARGIN: 0in 0in 0pt; mso-layout-grid-align: none" class=MsoNormal><SPAN style="FONT-FAMILY: NSimSun; FONT-SIZE: 9pt; mso-bidi-font-family: NSimSun"><SPAN style="mso-spacerun: yes">&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp; </SPAN><SPAN style="COLOR: blue">get</SPAN>;<o:p></o:p></SPAN></P>
<P style="LINE-HEIGHT: normal; MARGIN: 0in 0in 0pt; mso-layout-grid-align: none" class=MsoNormal><SPAN style="FONT-FAMILY: NSimSun; FONT-SIZE: 9pt; mso-bidi-font-family: NSimSun"><SPAN style="mso-spacerun: yes">&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp; </SPAN><SPAN style="COLOR: blue">set</SPAN>;<o:p></o:p></SPAN></P>
<P style="LINE-HEIGHT: normal; MARGIN: 0in 0in 0pt; mso-layout-grid-align: none" class=MsoNormal><SPAN style="FONT-FAMILY: NSimSun; FONT-SIZE: 9pt; mso-bidi-font-family: NSimSun"><SPAN style="mso-spacerun: yes">&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp; </SPAN>}<o:p></o:p></SPAN></P>
<P style="LINE-HEIGHT: normal; MARGIN: 0in 0in 0pt; mso-layout-grid-align: none" class=MsoNormal><SPAN style="FONT-FAMILY: NSimSun; FONT-SIZE: 9pt; mso-bidi-font-family: NSimSun"><o:p>&nbsp;</o:p></SPAN></P>
<P style="LINE-HEIGHT: normal; MARGIN: 0in 0in 0pt; mso-layout-grid-align: none" class=MsoNormal><SPAN style="FONT-FAMILY: NSimSun; FONT-SIZE: 9pt; mso-bidi-font-family: NSimSun"><SPAN style="mso-spacerun: yes">&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp; </SPAN><SPAN style="COLOR: blue">public</SPAN> <SPAN style="COLOR: #2b91af">Collection</SPAN>&lt;<SPAN style="COLOR: #2b91af">InArgument</SPAN>&gt; Args<o:p></o:p></SPAN></P>
<P style="LINE-HEIGHT: normal; MARGIN: 0in 0in 0pt; mso-layout-grid-align: none" class=MsoNormal><SPAN style="FONT-FAMILY: NSimSun; FONT-SIZE: 9pt; mso-bidi-font-family: NSimSun"><SPAN style="mso-spacerun: yes">&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp; </SPAN>{<o:p></o:p></SPAN></P>
<P style="LINE-HEIGHT: normal; MARGIN: 0in 0in 0pt; mso-layout-grid-align: none" class=MsoNormal><SPAN style="FONT-FAMILY: NSimSun; FONT-SIZE: 9pt; mso-bidi-font-family: NSimSun"><SPAN style="mso-spacerun: yes">&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp; </SPAN><SPAN style="COLOR: blue">get</SPAN> { <SPAN style="COLOR: blue">return</SPAN> <SPAN style="COLOR: blue">this</SPAN>.args; }<o:p></o:p></SPAN></P>
<P style="LINE-HEIGHT: normal; MARGIN: 0in 0in 0pt; mso-layout-grid-align: none" class=MsoNormal><SPAN style="FONT-FAMILY: NSimSun; FONT-SIZE: 9pt; mso-bidi-font-family: NSimSun"><SPAN style="mso-spacerun: yes">&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp; </SPAN>}<o:p></o:p></SPAN></P>
<P style="LINE-HEIGHT: normal; MARGIN: 0in 0in 0pt; mso-layout-grid-align: none" class=MsoNormal><SPAN style="FONT-FAMILY: NSimSun; FONT-SIZE: 9pt; mso-bidi-font-family: NSimSun"><o:p>&nbsp;</o:p></SPAN></P>
<P style="LINE-HEIGHT: normal; MARGIN: 0in 0in 0pt; mso-layout-grid-align: none" class=MsoNormal><SPAN style="FONT-FAMILY: NSimSun; FONT-SIZE: 9pt; mso-bidi-font-family: NSimSun"><SPAN style="mso-spacerun: yes">&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp; </SPAN><SPAN style="COLOR: blue">protected</SPAN> <SPAN style="COLOR: blue">override</SPAN> <SPAN style="COLOR: blue">void</SPAN> CacheMetadata(<SPAN style="COLOR: #2b91af">CodeActivityMetadata</SPAN> metadata)<o:p></o:p></SPAN></P>
<P style="LINE-HEIGHT: normal; MARGIN: 0in 0in 0pt; mso-layout-grid-align: none" class=MsoNormal><SPAN style="FONT-FAMILY: NSimSun; FONT-SIZE: 9pt; mso-bidi-font-family: NSimSun"><SPAN style="mso-spacerun: yes">&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp; </SPAN>{<o:p></o:p></SPAN></P>
<P style="LINE-HEIGHT: normal; MARGIN: 0in 0in 0pt; mso-layout-grid-align: none" class=MsoNormal><SPAN style="FONT-FAMILY: NSimSun; FONT-SIZE: 9pt; mso-bidi-font-family: NSimSun"><SPAN style="mso-spacerun: yes">&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp; </SPAN><SPAN style="COLOR: #2b91af">RuntimeArgument</SPAN> formatArgument = <SPAN style="COLOR: blue">new</SPAN> <SPAN style="COLOR: #2b91af">RuntimeArgument</SPAN>(<SPAN style="COLOR: #a31515">"Format"</SPAN>, <SPAN style="COLOR: blue">typeof</SPAN>(<SPAN style="COLOR: blue">string</SPAN>), <SPAN style="COLOR: #2b91af">ArgumentDirection</SPAN>.In);<o:p></o:p></SPAN></P>
<P style="LINE-HEIGHT: normal; MARGIN: 0in 0in 0pt; mso-layout-grid-align: none" class=MsoNormal><SPAN style="FONT-FAMILY: NSimSun; FONT-SIZE: 9pt; mso-bidi-font-family: NSimSun"><SPAN style="mso-spacerun: yes">&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp; </SPAN>metadata.Bind(<SPAN style="COLOR: blue">this</SPAN>.Format, formatArgument);<o:p></o:p></SPAN></P>
<P style="LINE-HEIGHT: normal; MARGIN: 0in 0in 0pt; mso-layout-grid-align: none" class=MsoNormal><SPAN style="FONT-FAMILY: NSimSun; FONT-SIZE: 9pt; mso-bidi-font-family: NSimSun"><SPAN style="mso-spacerun: yes">&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp; </SPAN>metadata.AddArgument(formatArgument);<o:p></o:p></SPAN></P>
<P style="LINE-HEIGHT: normal; MARGIN: 0in 0in 0pt; mso-layout-grid-align: none" class=MsoNormal><SPAN style="FONT-FAMILY: NSimSun; FONT-SIZE: 9pt; mso-bidi-font-family: NSimSun"><o:p>&nbsp;</o:p></SPAN></P>
<P style="LINE-HEIGHT: normal; MARGIN: 0in 0in 0pt; mso-layout-grid-align: none" class=MsoNormal><SPAN style="FONT-FAMILY: NSimSun; FONT-SIZE: 9pt; mso-bidi-font-family: NSimSun"><SPAN style="mso-spacerun: yes">&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp; </SPAN><SPAN style="COLOR: blue">for</SPAN> (<SPAN style="COLOR: blue">int</SPAN> i = <SPAN style="COLOR: brown">0</SPAN>; i &lt; <SPAN style="COLOR: blue">this</SPAN>.Args.Count; i++)<o:p></o:p></SPAN></P>
<P style="LINE-HEIGHT: normal; MARGIN: 0in 0in 0pt; mso-layout-grid-align: none" class=MsoNormal><SPAN style="FONT-FAMILY: NSimSun; FONT-SIZE: 9pt; mso-bidi-font-family: NSimSun"><SPAN style="mso-spacerun: yes">&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp; </SPAN>{<o:p></o:p></SPAN></P>
<P style="LINE-HEIGHT: normal; MARGIN: 0in 0in 0pt; mso-layout-grid-align: none" class=MsoNormal><SPAN style="FONT-FAMILY: NSimSun; FONT-SIZE: 9pt; mso-bidi-font-family: NSimSun"><SPAN style="mso-spacerun: yes">&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp; </SPAN><SPAN style="COLOR: #2b91af">RuntimeArgument</SPAN> argArgument = <SPAN style="COLOR: blue">new</SPAN> <SPAN style="COLOR: #2b91af">RuntimeArgument</SPAN>(<SPAN style="COLOR: #a31515">"Arg"</SPAN> + i, <SPAN style="COLOR: blue">this</SPAN>.Args[i].ArgumentType, <SPAN style="COLOR: #2b91af">ArgumentDirection</SPAN>.In);<o:p></o:p></SPAN></P>
<P style="LINE-HEIGHT: normal; MARGIN: 0in 0in 0pt; mso-layout-grid-align: none" class=MsoNormal><SPAN style="FONT-FAMILY: NSimSun; FONT-SIZE: 9pt; mso-bidi-font-family: NSimSun"><SPAN style="mso-spacerun: yes">&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp; </SPAN>metadata.Bind(<SPAN style="COLOR: blue">this</SPAN>.Args[i], argArgument);<o:p></o:p></SPAN></P>
<P style="LINE-HEIGHT: normal; MARGIN: 0in 0in 0pt; mso-layout-grid-align: none" class=MsoNormal><SPAN style="FONT-FAMILY: NSimSun; FONT-SIZE: 9pt; mso-bidi-font-family: NSimSun"><SPAN style="mso-spacerun: yes">&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp; </SPAN>metadata.AddArgument(argArgument);<o:p></o:p></SPAN></P>
<P style="LINE-HEIGHT: normal; MARGIN: 0in 0in 0pt; mso-layout-grid-align: none" class=MsoNormal><SPAN style="FONT-FAMILY: NSimSun; FONT-SIZE: 9pt; mso-bidi-font-family: NSimSun"><SPAN style="mso-spacerun: yes">&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp; </SPAN>}<o:p></o:p></SPAN></P>
<P style="LINE-HEIGHT: normal; MARGIN: 0in 0in 0pt; mso-layout-grid-align: none" class=MsoNormal><SPAN style="FONT-FAMILY: NSimSun; FONT-SIZE: 9pt; mso-bidi-font-family: NSimSun"><SPAN style="mso-spacerun: yes">&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp; </SPAN>}<o:p></o:p></SPAN></P>
<P style="LINE-HEIGHT: normal; MARGIN: 0in 0in 0pt; mso-layout-grid-align: none" class=MsoNormal><SPAN style="FONT-FAMILY: NSimSun; FONT-SIZE: 9pt; mso-bidi-font-family: NSimSun"><o:p>&nbsp;</o:p></SPAN></P>
<P style="LINE-HEIGHT: normal; MARGIN: 0in 0in 0pt; mso-layout-grid-align: none" class=MsoNormal><SPAN style="FONT-FAMILY: NSimSun; FONT-SIZE: 9pt; mso-bidi-font-family: NSimSun"><SPAN style="mso-spacerun: yes">&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp; </SPAN><SPAN style="COLOR: blue">protected</SPAN> <SPAN style="COLOR: blue">override</SPAN> <SPAN style="COLOR: blue">void</SPAN> Execute(<SPAN style="COLOR: #2b91af">CodeActivityContext</SPAN> context)<o:p></o:p></SPAN></P>
<P style="LINE-HEIGHT: normal; MARGIN: 0in 0in 0pt; mso-layout-grid-align: none" class=MsoNormal><SPAN style="FONT-FAMILY: NSimSun; FONT-SIZE: 9pt; mso-bidi-font-family: NSimSun"><SPAN style="mso-spacerun: yes">&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp; </SPAN>{<o:p></o:p></SPAN></P>
<P style="LINE-HEIGHT: normal; MARGIN: 0in 0in 0pt; mso-layout-grid-align: none" class=MsoNormal><SPAN style="FONT-FAMILY: NSimSun; FONT-SIZE: 9pt; mso-bidi-font-family: NSimSun"><SPAN style="mso-spacerun: yes">&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp; </SPAN><SPAN style="COLOR: blue">string</SPAN> format = <SPAN style="COLOR: blue">this</SPAN>.Format.Get(context);<o:p></o:p></SPAN></P>
<P style="LINE-HEIGHT: normal; MARGIN: 0in 0in 0pt; mso-layout-grid-align: none" class=MsoNormal><SPAN style="FONT-FAMILY: NSimSun; FONT-SIZE: 9pt; mso-bidi-font-family: NSimSun"><SPAN style="mso-spacerun: yes">&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp; </SPAN><SPAN style="COLOR: blue">object</SPAN>[] arguments = <SPAN style="COLOR: blue">new</SPAN> <SPAN style="COLOR: blue">object</SPAN>[<SPAN style="COLOR: blue">this</SPAN>.Args.Count];<o:p></o:p></SPAN></P>
<P style="LINE-HEIGHT: normal; MARGIN: 0in 0in 0pt; mso-layout-grid-align: none" class=MsoNormal><SPAN style="FONT-FAMILY: NSimSun; FONT-SIZE: 9pt; mso-bidi-font-family: NSimSun"><SPAN style="mso-spacerun: yes">&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp; </SPAN><SPAN style="COLOR: blue">for</SPAN> (<SPAN style="COLOR: blue">int</SPAN> i = <SPAN style="COLOR: brown">0</SPAN>; i &lt; <SPAN style="COLOR: blue">this</SPAN>.Args.Count; i++)<o:p></o:p></SPAN></P>
<P style="LINE-HEIGHT: normal; MARGIN: 0in 0in 0pt; mso-layout-grid-align: none" class=MsoNormal><SPAN style="FONT-FAMILY: NSimSun; FONT-SIZE: 9pt; mso-bidi-font-family: NSimSun"><SPAN style="mso-spacerun: yes">&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp; </SPAN>{<o:p></o:p></SPAN></P>
<P style="LINE-HEIGHT: normal; MARGIN: 0in 0in 0pt; mso-layout-grid-align: none" class=MsoNormal><SPAN style="FONT-FAMILY: NSimSun; FONT-SIZE: 9pt; mso-bidi-font-family: NSimSun"><SPAN style="mso-spacerun: yes">&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp; </SPAN>arguments[i] = <SPAN style="COLOR: blue">this</SPAN>.Args[i].Get(context);<o:p></o:p></SPAN></P>
<P style="LINE-HEIGHT: normal; MARGIN: 0in 0in 0pt; mso-layout-grid-align: none" class=MsoNormal><SPAN style="FONT-FAMILY: NSimSun; FONT-SIZE: 9pt; mso-bidi-font-family: NSimSun"><SPAN style="mso-spacerun: yes">&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp; </SPAN>}<o:p></o:p></SPAN></P>
<P style="LINE-HEIGHT: normal; MARGIN: 0in 0in 0pt; mso-layout-grid-align: none" class=MsoNormal><SPAN style="FONT-FAMILY: NSimSun; FONT-SIZE: 9pt; mso-bidi-font-family: NSimSun"><SPAN style="mso-spacerun: yes">&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp; </SPAN><SPAN style="COLOR: #2b91af">Console</SPAN>.WriteLine(format, arguments);<o:p></o:p></SPAN></P>
<P style="LINE-HEIGHT: normal; MARGIN: 0in 0in 0pt; mso-layout-grid-align: none" class=MsoNormal><SPAN style="FONT-FAMILY: NSimSun; FONT-SIZE: 9pt; mso-bidi-font-family: NSimSun"><SPAN style="mso-spacerun: yes">&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp; </SPAN>}<o:p></o:p></SPAN></P>
<P style="LINE-HEIGHT: normal; MARGIN: 0in 0in 0pt; mso-layout-grid-align: none" class=MsoNormal><SPAN style="FONT-FAMILY: NSimSun; FONT-SIZE: 9pt; mso-bidi-font-family: NSimSun"><SPAN style="mso-spacerun: yes">&nbsp;&nbsp;&nbsp; </SPAN>}<o:p></o:p></SPAN></P>
<P style="MARGIN: 0in 0in 10pt" class=MsoCaption><STRONG><FONT color=#4f81bd><FONT face=Calibri><SPAN style="mso-spacerun: yes">&nbsp;</SPAN><SPAN style="mso-spacerun: yes">&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp; </SPAN>Code <SPAN style="mso-no-proof: yes">7</SPAN>. How to declare and use dynamic arguments<o:p></o:p></FONT></FONT></STRONG></P>
<P style="MARGIN: 0in 0in 10pt" class=MsoNormal><FONT size=3><FONT face=Calibri>Base implementation of CacheMetadata would not know how to handle the Args collection, so overriding the method is necessary.<o:p></o:p></FONT></FONT></P>
<P style="MARGIN: 0in 0in 10pt" class=MsoNormal><FONT size=3><FONT face=Calibri>There is a special case for argument definition. If a C# method only has one output, there is no need to declare an out argument. Generally people would just use the return result, which is really a implicit and unnamed output argument. <SPAN style="mso-spacerun: yes">&nbsp;</SPAN>WF4 uses the same paradigm to simplify programming experience. If an Activity is derived from base class Activity&lt;T&gt;, it will inherit an out argument called “Result”. There is no need to explicitly declare this argument unless CacheMetadata is overridden.<o:p></o:p></FONT></FONT></P>
<H2 style="MARGIN: auto 0in"><SPAN style="FONT-FAMILY: 'Cambria','serif'; COLOR: #365f91; FONT-SIZE: 12pt; mso-bidi-font-family: 'Times New Roman'; mso-fareast-font-family: 宋体; mso-ascii-theme-font: major-latin; mso-hansi-theme-font: major-latin; mso-fareast-theme-font: major-fareast; mso-bidi-theme-font: major-bidi; mso-themecolor: accent1; mso-themeshade: 191">Argument binding and evaluation<o:p></o:p></SPAN></H2>
<P style="MARGIN: 0in 0in 10pt" class=MsoNormal><FONT size=3><FONT face=Calibri>In C#, caller of a method could use an expression to define runtime value of an argument to the method. The expression could be a constant value, a variable, a math expression, or any programming structure with a value. For example:<o:p></o:p></FONT></FONT></P>
<P style="LINE-HEIGHT: normal; MARGIN: 0in 0in 0pt; mso-layout-grid-align: none" class=MsoNormal><SPAN style="FONT-FAMILY: NSimSun; COLOR: blue; FONT-SIZE: 9pt; mso-bidi-font-family: NSimSun"><SPAN style="mso-spacerun: yes">&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp; </SPAN>static</SPAN><SPAN style="FONT-FAMILY: NSimSun; FONT-SIZE: 9pt; mso-bidi-font-family: NSimSun"> <SPAN style="COLOR: blue">void</SPAN> Foo(<SPAN style="COLOR: blue">int</SPAN> x);<o:p></o:p></SPAN></P>
<P style="LINE-HEIGHT: normal; MARGIN: 0in 0in 0pt; mso-layout-grid-align: none" class=MsoNormal><SPAN style="FONT-FAMILY: NSimSun; COLOR: blue; FONT-SIZE: 9pt; mso-bidi-font-family: NSimSun"><SPAN style="mso-spacerun: yes">&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp; </SPAN></SPAN><SPAN style="FONT-FAMILY: NSimSun; FONT-SIZE: 9pt; mso-bidi-font-family: NSimSun">…<SPAN style="COLOR: blue"><o:p></o:p></SPAN></SPAN></P>
<P style="LINE-HEIGHT: normal; MARGIN: 0in 0in 0pt; mso-layout-grid-align: none" class=MsoNormal><SPAN style="FONT-FAMILY: NSimSun; COLOR: blue; FONT-SIZE: 9pt; mso-bidi-font-family: NSimSun"><SPAN style="mso-spacerun: yes">&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp; </SPAN>int</SPAN><SPAN style="FONT-FAMILY: NSimSun; FONT-SIZE: 9pt; mso-bidi-font-family: NSimSun"> a = …;<o:p></o:p></SPAN></P>
<P style="LINE-HEIGHT: normal; MARGIN: 0in 0in 0pt; mso-layout-grid-align: none" class=MsoNormal><SPAN style="FONT-FAMILY: NSimSun; FONT-SIZE: 9pt; mso-bidi-font-family: NSimSun"><SPAN style="mso-spacerun: yes">&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp; </SPAN>Foo(<SPAN style="COLOR: brown">5</SPAN>);<o:p></o:p></SPAN></P>
<P style="LINE-HEIGHT: normal; MARGIN: 0in 0in 0pt; mso-layout-grid-align: none" class=MsoNormal><SPAN style="FONT-FAMILY: NSimSun; FONT-SIZE: 9pt; mso-bidi-font-family: NSimSun"><SPAN style="mso-spacerun: yes">&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp; </SPAN>Foo(a);<o:p></o:p></SPAN></P>
<P style="LINE-HEIGHT: normal; MARGIN: 0in 0in 0pt; mso-layout-grid-align: none" class=MsoNormal><SPAN style="FONT-FAMILY: NSimSun; FONT-SIZE: 9pt; mso-bidi-font-family: NSimSun"><SPAN style="mso-spacerun: yes">&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp; </SPAN>Foo(<SPAN style="COLOR: blue">new</SPAN> <SPAN style="COLOR: #2b91af">Random</SPAN>().Next());<o:p></o:p></SPAN></P>
<P style="MARGIN: 0in 0in 10pt" class=MsoCaption><STRONG><FONT color=#4f81bd><FONT face=Calibri><SPAN style="mso-spacerun: yes">&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp; </SPAN>Code <SPAN style="mso-no-proof: yes">8</SPAN>. Argument binding in C#<o:p></o:p></FONT></FONT></STRONG></P>
<P style="MARGIN: 0in 0in 10pt" class=MsoNormal><FONT size=3><FONT face=Calibri>Similarly, in WF, users of an Activity need to provide expressions for its arguments. Activity is the basic unit of WF program.<SPAN style="mso-spacerun: yes">&nbsp; </SPAN>So an expression in WF is just an Activity which has a return value, a subclass of Activity&lt;T&gt;. WF also defines a base class for Activity&lt;T&gt;, called ActivityWithResult:<o:p></o:p></FONT></FONT></P>
<P style="LINE-HEIGHT: normal; MARGIN: 0in 0in 0pt; mso-layout-grid-align: none" class=MsoNormal><SPAN style="FONT-FAMILY: NSimSun; COLOR: blue; FONT-SIZE: 9pt; mso-bidi-font-family: NSimSun"><SPAN style="mso-spacerun: yes">&nbsp;&nbsp;&nbsp; </SPAN>public</SPAN><SPAN style="FONT-FAMILY: NSimSun; FONT-SIZE: 9pt; mso-bidi-font-family: NSimSun"> <SPAN style="COLOR: blue">abstract</SPAN> <SPAN style="COLOR: blue">class</SPAN> <SPAN style="COLOR: #2b91af">ActivityWithResult</SPAN> : <SPAN style="COLOR: #2b91af">Activity</SPAN><o:p></o:p></SPAN></P>
<P style="LINE-HEIGHT: normal; MARGIN: 0in 0in 0pt; mso-layout-grid-align: none" class=MsoNormal><SPAN style="FONT-FAMILY: NSimSun; FONT-SIZE: 9pt; mso-bidi-font-family: NSimSun"><SPAN style="mso-spacerun: yes">&nbsp;&nbsp;&nbsp; </SPAN>{<o:p></o:p></SPAN></P>
<P style="LINE-HEIGHT: normal; MARGIN: 0in 0in 0pt; mso-layout-grid-align: none" class=MsoNormal><SPAN style="FONT-FAMILY: NSimSun; FONT-SIZE: 9pt; mso-bidi-font-family: NSimSun"><SPAN style="mso-spacerun: yes">&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp; </SPAN><SPAN style="COLOR: blue">public</SPAN> <SPAN style="COLOR: #2b91af">OutArgument</SPAN> Result { <SPAN style="COLOR: blue">get</SPAN>; <SPAN style="COLOR: blue">set</SPAN>; }<o:p></o:p></SPAN></P>
<P style="LINE-HEIGHT: normal; MARGIN: 0in 0in 0pt; mso-layout-grid-align: none" class=MsoNormal><SPAN style="FONT-FAMILY: NSimSun; FONT-SIZE: 9pt; mso-bidi-font-family: NSimSun"><SPAN style="mso-spacerun: yes">&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp; </SPAN><SPAN style="COLOR: blue">public</SPAN> <SPAN style="COLOR: #2b91af">Type</SPAN> ResultType { <SPAN style="COLOR: blue">get</SPAN>; }<o:p></o:p></SPAN></P>
<P style="LINE-HEIGHT: normal; MARGIN: 0in 0in 0pt; mso-layout-grid-align: none" class=MsoNormal><SPAN style="FONT-FAMILY: NSimSun; FONT-SIZE: 9pt; mso-bidi-font-family: NSimSun"><SPAN style="mso-spacerun: yes">&nbsp;&nbsp;&nbsp; </SPAN>}<o:p></o:p></SPAN></P>
<P style="MARGIN: 0in 0in 10pt" class=MsoCaption><STRONG><FONT color=#4f81bd><FONT face=Calibri><SPAN style="mso-spacerun: yes">&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp; </SPAN>Code <SPAN style="mso-no-proof: yes">9</SPAN>. ActivityWithResult<o:p></o:p></FONT></FONT></STRONG></P>
<P style="MARGIN: 0in 0in 10pt" class=MsoNormal><FONT face=Calibri><FONT size=3>As showed before, Argument.Expression is defined as an ActivityWithResult. So client of an Activity needs to bind arguments to some Activities with return result. WF has defined some Activities for common expressions.<o:p></o:p></FONT></FONT></P>
<P style="TEXT-INDENT: -0.25in; MARGIN: 0in 0in 10pt 0.5in; mso-list: l0 level1 lfo1" class=MsoListParagraph><SPAN style="FONT-FAMILY: Symbol; mso-bidi-font-family: Symbol; mso-fareast-font-family: Symbol"><SPAN style="mso-list: Ignore"><FONT size=3>·</FONT><SPAN style="FONT: 7pt 'Times New Roman'">&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp; </SPAN></SPAN></SPAN><FONT size=3><FONT face=Calibri>Literal&lt;T&gt;: models literal value. T could only be string and value types. Sample usage:<o:p></o:p></FONT></FONT></P>
<P style="LINE-HEIGHT: normal; MARGIN: 0in 0in 0pt 0.5in; mso-layout-grid-align: none" class=MsoNormal><SPAN style="FONT-FAMILY: NSimSun; COLOR: #2b91af; FONT-SIZE: 9pt; mso-bidi-font-family: NSimSun">MyWriteLine</SPAN><SPAN style="FONT-FAMILY: NSimSun; FONT-SIZE: 9pt; mso-bidi-font-family: NSimSun"> writeLine = <SPAN style="COLOR: blue">new</SPAN> <SPAN style="COLOR: #2b91af">MyWriteLine</SPAN><o:p></o:p></SPAN></P>
<P style="LINE-HEIGHT: normal; MARGIN: 0in 0in 0pt 0.5in; mso-layout-grid-align: none" class=MsoNormal><SPAN style="FONT-FAMILY: NSimSun; FONT-SIZE: 9pt; mso-bidi-font-family: NSimSun"><SPAN style="mso-spacerun: yes">&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp; </SPAN>{<o:p></o:p></SPAN></P>
<P style="LINE-HEIGHT: normal; MARGIN: 0in 0in 0pt 0.5in; mso-layout-grid-align: none" class=MsoNormal><SPAN style="FONT-FAMILY: NSimSun; FONT-SIZE: 9pt; mso-bidi-font-family: NSimSun"><SPAN style="mso-spacerun: yes">&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp; </SPAN>Format = <SPAN style="COLOR: blue">new</SPAN> <SPAN style="COLOR: #2b91af">InArgument</SPAN>&lt;<SPAN style="COLOR: blue">string</SPAN>&gt; { Expression = <SPAN style="COLOR: blue">new</SPAN> <SPAN style="COLOR: #2b91af">Literal</SPAN>&lt;<SPAN style="COLOR: blue">string</SPAN>&gt; (<SPAN style="COLOR: #a31515">"{0}, {1}"</SPAN>)}<o:p></o:p></SPAN></P>
<P style="LINE-HEIGHT: normal; MARGIN: 0in 0in 0pt 0.5in; mso-layout-grid-align: none" class=MsoNormal><SPAN style="FONT-FAMILY: NSimSun; FONT-SIZE: 9pt; mso-bidi-font-family: NSimSun"><SPAN style="mso-spacerun: yes">&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp; </SPAN>};<o:p></o:p></SPAN></P>
<P style="MARGIN: 0in 0in 10pt" class=MsoCaption><STRONG><FONT color=#4f81bd><FONT face=Calibri><SPAN style="mso-spacerun: yes">&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp; </SPAN>Code <SPAN style="mso-no-proof: yes">10</SPAN>. Sample usage of Literal&lt;T&gt;<SPAN style="FONT-FAMILY: NSimSun; mso-bidi-font-family: NSimSun"><o:p></o:p></SPAN></FONT></FONT></STRONG></P>
<P style="MARGIN: 0in 0in 10pt 0.5in" class=MsoListParagraph><FONT size=3><FONT face=Calibri>Argument has constructor to take literal value and create Literal&lt;T&gt; internally, so the code could be simplified as:<o:p></o:p></FONT></FONT></P>
<P style="LINE-HEIGHT: normal; MARGIN: 0in 0in 0pt; mso-layout-grid-align: none" class=MsoNormal><SPAN style="FONT-FAMILY: NSimSun; COLOR: #2b91af; FONT-SIZE: 9pt; mso-bidi-font-family: NSimSun"><SPAN style="mso-spacerun: yes">&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp; </SPAN>MyWriteLine</SPAN><SPAN style="FONT-FAMILY: NSimSun; FONT-SIZE: 9pt; mso-bidi-font-family: NSimSun"> writeLine = <SPAN style="COLOR: blue">new</SPAN> <SPAN style="COLOR: #2b91af">MyWriteLine</SPAN><o:p></o:p></SPAN></P>
<P style="LINE-HEIGHT: normal; MARGIN: 0in 0in 0pt; mso-layout-grid-align: none" class=MsoNormal><SPAN style="FONT-FAMILY: NSimSun; FONT-SIZE: 9pt; mso-bidi-font-family: NSimSun"><SPAN style="mso-spacerun: yes">&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp; </SPAN>{<o:p></o:p></SPAN></P>
<P style="LINE-HEIGHT: normal; MARGIN: 0in 0in 0pt; mso-layout-grid-align: none" class=MsoNormal><SPAN style="FONT-FAMILY: NSimSun; FONT-SIZE: 9pt; mso-bidi-font-family: NSimSun"><SPAN style="mso-spacerun: yes">&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp; </SPAN>Format = <SPAN style="COLOR: blue">new</SPAN> <SPAN style="COLOR: #2b91af">InArgument</SPAN>&lt;<SPAN style="COLOR: blue">string</SPAN>&gt;(<SPAN style="COLOR: #a31515">"{0}, {1}"</SPAN>)<o:p></o:p></SPAN></P>
<P style="LINE-HEIGHT: normal; MARGIN: 0in 0in 0pt; mso-layout-grid-align: none" class=MsoNormal><SPAN style="FONT-FAMILY: NSimSun; FONT-SIZE: 9pt; mso-bidi-font-family: NSimSun"><SPAN style="mso-spacerun: yes">&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp; </SPAN>};<o:p></o:p></SPAN></P>
<P style="MARGIN: 0in 0in 10pt" class=MsoCaption><STRONG><FONT color=#4f81bd><FONT face=Calibri><SPAN style="mso-spacerun: yes">&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp; </SPAN>Code <SPAN style="mso-no-proof: yes">11</SPAN>. Sample usage of Literal&lt;T&gt;<o:p></o:p></FONT></FONT></STRONG></P>
<P style="TEXT-INDENT: -0.25in; MARGIN: 0in 0in 10pt 0.5in; mso-list: l0 level1 lfo1" class=MsoListParagraph><SPAN style="FONT-FAMILY: Symbol; mso-bidi-font-family: Symbol; mso-fareast-font-family: Symbol"><SPAN style="mso-list: Ignore"><FONT size=3>·</FONT><SPAN style="FONT: 7pt 'Times New Roman'">&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp; </SPAN></SPAN></SPAN><FONT size=3><FONT face=Calibri>VariableValue&lt;T&gt;: models accessing value of a variable. Sample usage:<o:p></o:p></FONT></FONT></P>
<P style="LINE-HEIGHT: normal; MARGIN: 0in 0in 0pt; mso-layout-grid-align: none" class=MsoNormal><SPAN style="FONT-FAMILY: NSimSun; COLOR: #2b91af; FONT-SIZE: 9pt; mso-bidi-font-family: NSimSun"><SPAN style="mso-spacerun: yes">&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp; </SPAN>MyWriteLine</SPAN><SPAN style="FONT-FAMILY: NSimSun; FONT-SIZE: 9pt; mso-bidi-font-family: NSimSun"> writeLine = <SPAN style="COLOR: blue">new</SPAN> <SPAN style="COLOR: #2b91af">MyWriteLine</SPAN><o:p></o:p></SPAN></P>
<P style="LINE-HEIGHT: normal; MARGIN: 0in 0in 0pt; mso-layout-grid-align: none" class=MsoNormal><SPAN style="FONT-FAMILY: NSimSun; FONT-SIZE: 9pt; mso-bidi-font-family: NSimSun"><SPAN style="mso-spacerun: yes">&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp; </SPAN>{<o:p></o:p></SPAN></P>
<P style="LINE-HEIGHT: normal; MARGIN: 0in 0in 0pt; mso-layout-grid-align: none" class=MsoNormal><SPAN style="FONT-FAMILY: NSimSun; FONT-SIZE: 9pt; mso-bidi-font-family: NSimSun"><SPAN style="mso-spacerun: yes">&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp; </SPAN>Format = <SPAN style="COLOR: blue">new</SPAN> <SPAN style="COLOR: #2b91af">InArgument</SPAN>&lt;<SPAN style="COLOR: blue">string</SPAN>&gt; { Expression = <SPAN style="COLOR: blue">new</SPAN> <SPAN style="COLOR: #2b91af">VariableValue</SPAN>&lt;T&gt;(a)} <SPAN style="COLOR: green">//a is a WF variable, of type Variable</SPAN><o:p></o:p></SPAN></P>
<P style="LINE-HEIGHT: normal; MARGIN: 0in 0in 0pt; mso-layout-grid-align: none" class=MsoNormal><SPAN style="FONT-FAMILY: NSimSun; FONT-SIZE: 9pt; mso-bidi-font-family: NSimSun"><SPAN style="mso-spacerun: yes">&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp; </SPAN>};<o:p></o:p></SPAN></P>
<P style="MARGIN: 0in 0in 10pt" class=MsoCaption><STRONG><FONT color=#4f81bd><SPAN style="FONT-FAMILY: NSimSun; mso-bidi-font-family: NSimSun"><SPAN style="mso-spacerun: yes">&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp; </SPAN></SPAN><FONT face=Calibri>Code <SPAN style="mso-no-proof: yes">12</SPAN>. Sample usage of VariableValue&lt;T&gt;<o:p></o:p></FONT></FONT></STRONG></P>
<P style="MARGIN: 0in 0in 10pt 0.5in" class=MsoNormal><FONT size=3><FONT face=Calibri>Argument also has constructor to take Variable and create VariableValue&lt;T&gt; internally, so the code could be simplified as:<o:p></o:p></FONT></FONT></P>
<P style="LINE-HEIGHT: normal; MARGIN: 0in 0in 0pt; mso-layout-grid-align: none" class=MsoNormal><SPAN style="FONT-FAMILY: NSimSun; COLOR: #2b91af; FONT-SIZE: 9pt; mso-bidi-font-family: NSimSun"><SPAN style="mso-spacerun: yes">&nbsp;</SPAN><SPAN style="mso-spacerun: yes">&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp; </SPAN>MyWriteLine</SPAN><SPAN style="FONT-FAMILY: NSimSun; FONT-SIZE: 9pt; mso-bidi-font-family: NSimSun"> writeLine = <SPAN style="COLOR: blue">new</SPAN> <SPAN style="COLOR: #2b91af">MyWriteLine</SPAN><o:p></o:p></SPAN></P>
<P style="LINE-HEIGHT: normal; MARGIN: 0in 0in 0pt; mso-layout-grid-align: none" class=MsoNormal><SPAN style="FONT-FAMILY: NSimSun; FONT-SIZE: 9pt; mso-bidi-font-family: NSimSun"><SPAN style="mso-spacerun: yes">&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp; </SPAN>{<o:p></o:p></SPAN></P>
<P style="LINE-HEIGHT: normal; MARGIN: 0in 0in 0pt; mso-layout-grid-align: none" class=MsoNormal><SPAN style="FONT-FAMILY: NSimSun; FONT-SIZE: 9pt; mso-bidi-font-family: NSimSun"><SPAN style="mso-spacerun: yes">&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp; </SPAN>Format = <SPAN style="COLOR: blue">new</SPAN> <SPAN style="COLOR: #2b91af">InArgument</SPAN>&lt;<SPAN style="COLOR: blue">string</SPAN>&gt;(a) <SPAN style="COLOR: green">//a is a WF variable, of type Variable</SPAN><o:p></o:p></SPAN></P>
<P style="LINE-HEIGHT: normal; MARGIN: 0in 0in 0pt; mso-layout-grid-align: none" class=MsoNormal><SPAN style="FONT-FAMILY: NSimSun; FONT-SIZE: 9pt; mso-bidi-font-family: NSimSun"><SPAN style="mso-spacerun: yes">&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp; </SPAN>};<o:p></o:p></SPAN></P>
<P style="MARGIN: 0in 0in 10pt" class=MsoCaption><STRONG><FONT color=#4f81bd><FONT face=Calibri><SPAN style="mso-spacerun: yes">&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp; </SPAN>Code <SPAN style="mso-no-proof: yes">13</SPAN>. Sample usage of VariableValue&lt;T&gt;<o:p></o:p></FONT></FONT></STRONG></P>
<P style="MARGIN: 0in 0in 10pt" class=MsoNormal><FONT face=Calibri><FONT size=3><SPAN style="mso-tab-count: 1">&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp; </SPAN>To bind a variable to an OutArgument as L-value, one could use VariableReference&lt;T&gt;.<o:p></o:p></FONT></FONT></P>
<P style="TEXT-INDENT: -0.25in; MARGIN: 0in 0in 10pt 0.5in; mso-list: l0 level1 lfo1" class=MsoListParagraph><SPAN style="FONT-FAMILY: Symbol; mso-bidi-font-family: Symbol; mso-fareast-font-family: Symbol"><SPAN style="mso-list: Ignore"><FONT size=3>·</FONT><SPAN style="FONT: 7pt 'Times New Roman'">&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp; </SPAN></SPAN></SPAN><FONT size=3><FONT face=Calibri>VisualBasicValue&lt;T&gt;: models an expression written in VB string. Symbols like WF variable and argument name could be used in the expression string. Sample usage:<o:p></o:p></FONT></FONT></P>
<P style="LINE-HEIGHT: normal; MARGIN: 0in 0in 0pt 0.5in; mso-layout-grid-align: none" class=MsoNormal><SPAN style="FONT-FAMILY: NSimSun; COLOR: #2b91af; FONT-SIZE: 9pt; mso-bidi-font-family: NSimSun">MyWriteLine</SPAN><SPAN style="FONT-FAMILY: NSimSun; FONT-SIZE: 9pt; mso-bidi-font-family: NSimSun"> writeLine = <SPAN style="COLOR: blue">new</SPAN> <SPAN style="COLOR: #2b91af">MyWriteLine</SPAN><o:p></o:p></SPAN></P>
<P style="LINE-HEIGHT: normal; MARGIN: 0in 0in 0pt 0.5in; mso-layout-grid-align: none" class=MsoNormal><SPAN style="FONT-FAMILY: NSimSun; FONT-SIZE: 9pt; mso-bidi-font-family: NSimSun"><SPAN style="mso-spacerun: yes">&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp; </SPAN>{<o:p></o:p></SPAN></P>
<P style="LINE-HEIGHT: normal; MARGIN: 0in 0in 0pt 0.5in; mso-layout-grid-align: none" class=MsoNormal><SPAN style="FONT-FAMILY: NSimSun; FONT-SIZE: 9pt; mso-bidi-font-family: NSimSun"><SPAN style="mso-spacerun: yes">&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp; </SPAN>Format = <SPAN style="COLOR: blue">new</SPAN> <SPAN style="COLOR: #2b91af">InArgument</SPAN>&lt;<SPAN style="COLOR: blue">string</SPAN>&gt; { Expression = <SPAN style="COLOR: blue">new</SPAN> <SPAN style="COLOR: #2b91af">VisualBasicValue</SPAN>&lt;<SPAN style="COLOR: blue">string</SPAN>&gt;(<SPAN style="COLOR: #a31515">"a + b"</SPAN>)} <SPAN style="COLOR: green">//a and b are both WF variables</SPAN><o:p></o:p></SPAN></P>
<P style="LINE-HEIGHT: normal; MARGIN: 0in 0in 0pt 0.5in; mso-layout-grid-align: none" class=MsoNormal><SPAN style="FONT-FAMILY: NSimSun; FONT-SIZE: 9pt; mso-bidi-font-family: NSimSun"><SPAN style="mso-spacerun: yes">&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp; </SPAN>};<o:p></o:p></SPAN></P>
<P style="MARGIN: 0in 0in 10pt" class=MsoCaption><STRONG><FONT color=#4f81bd><FONT face=Calibri><SPAN style="mso-spacerun: yes">&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp; </SPAN>Code <SPAN style="mso-no-proof: yes">14</SPAN>. Sample usage of VisualBasicValue&lt;T&gt;<o:p></o:p></FONT></FONT></STRONG></P>
<P style="MARGIN: 0in 0in 10pt 0.5in" class=MsoNormal><FONT size=3><FONT face=Calibri>There is no syntax sugar in Argument class to simplify the code. But WF visual designers have direct support of VisualBasicValue&lt;T&gt; so it’s easy to write expressions as VB language directly in designer.<o:p></o:p></FONT></FONT></P>
<P style="MARGIN: 0in 0in 10pt 0.5in" class=MsoNormal><FONT size=3><FONT face=Calibri>To bind a VB expression to an OutArgument as L-value, one could use VisualBasicReference&lt;T&gt;.<o:p></o:p></FONT></FONT></P>
<P style="MARGIN: 0in 0in 10pt" class=MsoNormal><FONT size=3><FONT face=Calibri>Developers could always implement their own version of Activity&lt;T&gt; for their own argument binding logic.<o:p></o:p></FONT></FONT></P>
<P mce_keep="true"><SPAN style="LINE-HEIGHT: 115%; FONT-FAMILY: 'Calibri','sans-serif'; FONT-SIZE: 11pt; mso-bidi-font-family: 'Times New Roman'; mso-fareast-font-family: 宋体; mso-ascii-theme-font: minor-latin; mso-hansi-theme-font: minor-latin; mso-fareast-theme-font: minor-fareast; mso-bidi-theme-font: minor-bidi; mso-ansi-language: EN-US; mso-fareast-language: ZH-CN; mso-bidi-language: AR-SA">When an Activity is scheduled, WF runtime will needs to evaluate expressions of all arguments of this activity before execute the activity. Evaluation process includes scheduling the ActivityWithResult, and getting the out argument Result after it completes. One thing worth mentioning is that runtime schedule all expressions at the same time as if they are in a Parallel Activity, rather than a predefined order like C#.</SPAN></P>
<P><STRONG><EM><A title="Workflow Activity Variable" href="http://blogs.msdn.com/flow/archive/2010/04/27/workflow-foundation-4-0-activity-data-model-iii.aspx" mce_href="http://blogs.msdn.com/flow/archive/2010/04/27/workflow-foundation-4-0-activity-data-model-iii.aspx">To be continued…</A></EM></STRONG></P>
<P>Yun Jin <BR>Development Lead <BR><A href="http://blogs.msdn.com/yunjin">http://blogs.msdn.com/yunjin</A></P>]]></content:encoded>
    </item>
    <item>
      <title>Workflow Foundation 4.0 Activity Data Model (I)</title>
      <link>https://docs.microsoft.com/archive/blogs/flow/workflow-foundation-4-0-activity-data-model-i</link>
      <pubDate>Mon, 05 Apr 2010 07:19:00 GMT</pubDate>
      <dc:creator><![CDATA[Yun Jin]]></dc:creator>
      <guid
        isPermaLink="false">https://blogs.msdn.microsoft.com/flow/2010/04/05/workflow-foundation-4-0-activity-data-model-i/</guid>
      <description><![CDATA[In previous blogs, we went through how define an Activity’s execution logic. But this is not enough....]]></description>
      <content:encoded><![CDATA[<P style="MARGIN: 0in 0in 10pt" class=MsoNormal><FONT size=3><FONT face=Calibri>In <A title="Workflow Activity Model" href="http://blogs.msdn.com/flow/archive/2010/01/24/lights-camera-activities-windows-workflow-foundation-s-activity-model.aspx" mce_href="http://blogs.msdn.com/flow/archive/2010/01/24/lights-camera-activities-windows-workflow-foundation-s-activity-model.aspx">previous blogs</A>, we went through how define an Activity’s execution logic. But this is not enough. To build any meaningful Activity, developers also need to the activity’s state and data flow. In this post, I’m going to talk about WF4’s Activity data model.<?xml:namespace prefix = o ns = "urn:schemas-microsoft-com:office:office" /><o:p></o:p></FONT></FONT></P>
<H1 style="MARGIN: 24pt 0in 0pt"><FONT size=5><FONT color=#365f91><FONT face=Cambria>Argument and Variable 101<o:p></o:p></FONT></FONT></FONT></H1>
<P style="MARGIN: 0in 0in 10pt" class=MsoNormal><FONT size=3><FONT face=Calibri></FONT></FONT>&nbsp;</P>
<P style="MARGIN: 0in 0in 10pt" class=MsoNormal><FONT size=3><FONT face=Calibri>WF is just another higher level programming language that share a lot of similarity with popular imperative procedural programming languages. So let’s first take a look at data model of a typical procedural language. Here is a C# code snippet.<o:p></o:p></FONT></FONT></P>
<P style="LINE-HEIGHT: normal; MARGIN: 0in 0in 0pt; mso-layout-grid-align: none" class=MsoNormal><SPAN style="FONT-FAMILY: NSimSun; COLOR: blue; FONT-SIZE: 9pt; mso-bidi-font-family: NSimSun"><SPAN style="mso-spacerun: yes">&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp; </SPAN>static</SPAN><SPAN style="FONT-FAMILY: NSimSun; FONT-SIZE: 9pt; mso-bidi-font-family: NSimSun"> <SPAN style="COLOR: blue">void</SPAN> Main(<SPAN style="COLOR: blue">string</SPAN>[] args)<o:p></o:p></SPAN></P>
<P style="LINE-HEIGHT: normal; MARGIN: 0in 0in 0pt; mso-layout-grid-align: none" class=MsoNormal><SPAN style="FONT-FAMILY: NSimSun; FONT-SIZE: 9pt; mso-bidi-font-family: NSimSun"><SPAN style="mso-spacerun: yes">&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp; </SPAN>{<o:p></o:p></SPAN></P>
<P style="LINE-HEIGHT: normal; MARGIN: 0in 0in 0pt; mso-layout-grid-align: none" class=MsoNormal><SPAN style="FONT-FAMILY: NSimSun; FONT-SIZE: 9pt; mso-bidi-font-family: NSimSun"><SPAN style="mso-spacerun: yes">&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp; </SPAN><SPAN style="COLOR: blue">string</SPAN> answer = Prompt(<SPAN style="COLOR: #a31515">"1+1=?"</SPAN>);<o:p></o:p></SPAN></P>
<P style="LINE-HEIGHT: normal; MARGIN: 0in 0in 0pt; mso-layout-grid-align: none" class=MsoNormal><SPAN style="FONT-FAMILY: NSimSun; FONT-SIZE: 9pt; mso-bidi-font-family: NSimSun"><SPAN style="mso-spacerun: yes">&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp; </SPAN><SPAN style="COLOR: #2b91af">Console</SPAN>.WriteLine(<SPAN style="COLOR: #a31515">"Answer is {0}"</SPAN>, answer);<o:p></o:p></SPAN></P>
<P style="LINE-HEIGHT: normal; MARGIN: 0in 0in 0pt; mso-layout-grid-align: none" class=MsoNormal><SPAN style="FONT-FAMILY: NSimSun; FONT-SIZE: 9pt; mso-bidi-font-family: NSimSun"><SPAN style="mso-spacerun: yes">&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp; </SPAN><SPAN style="COLOR: #2b91af">Console</SPAN>.ReadLine();<o:p></o:p></SPAN></P>
<P style="LINE-HEIGHT: normal; MARGIN: 0in 0in 0pt; mso-layout-grid-align: none" class=MsoNormal><SPAN style="FONT-FAMILY: NSimSun; FONT-SIZE: 9pt; mso-bidi-font-family: NSimSun"><SPAN style="mso-spacerun: yes">&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp; </SPAN>}<o:p></o:p></SPAN></P>
<P style="LINE-HEIGHT: normal; MARGIN: 0in 0in 0pt; mso-layout-grid-align: none" class=MsoNormal><SPAN style="FONT-FAMILY: NSimSun; FONT-SIZE: 9pt; mso-bidi-font-family: NSimSun"><o:p>&nbsp;</o:p></SPAN></P>
<P style="LINE-HEIGHT: normal; MARGIN: 0in 0in 0pt; mso-layout-grid-align: none" class=MsoNormal><SPAN style="FONT-FAMILY: NSimSun; FONT-SIZE: 9pt; mso-bidi-font-family: NSimSun"><SPAN style="mso-spacerun: yes">&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp; </SPAN><SPAN style="COLOR: blue">static</SPAN> <SPAN style="COLOR: blue">string</SPAN> Prompt(<SPAN style="COLOR: blue">string</SPAN> question)<o:p></o:p></SPAN></P>
<P style="LINE-HEIGHT: normal; MARGIN: 0in 0in 0pt; mso-layout-grid-align: none" class=MsoNormal><SPAN style="FONT-FAMILY: NSimSun; FONT-SIZE: 9pt; mso-bidi-font-family: NSimSun"><SPAN style="mso-spacerun: yes">&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp; </SPAN>{<o:p></o:p></SPAN></P>
<P style="LINE-HEIGHT: normal; MARGIN: 0in 0in 0pt; mso-layout-grid-align: none" class=MsoNormal><SPAN style="FONT-FAMILY: NSimSun; FONT-SIZE: 9pt; mso-bidi-font-family: NSimSun"><SPAN style="mso-spacerun: yes">&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp; </SPAN><SPAN style="COLOR: #2b91af">Console</SPAN>.WriteLine(<SPAN style="COLOR: #a31515">"Please enter your name:"</SPAN>);<o:p></o:p></SPAN></P>
<P style="LINE-HEIGHT: normal; MARGIN: 0in 0in 0pt; mso-layout-grid-align: none" class=MsoNormal><SPAN style="FONT-FAMILY: NSimSun; FONT-SIZE: 9pt; mso-bidi-font-family: NSimSun"><SPAN style="mso-spacerun: yes">&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp; </SPAN><SPAN style="COLOR: blue">string</SPAN> name = <SPAN style="COLOR: #2b91af">Console</SPAN>.ReadLine();<o:p></o:p></SPAN></P>
<P style="LINE-HEIGHT: normal; MARGIN: 0in 0in 0pt; mso-layout-grid-align: none" class=MsoNormal><SPAN style="FONT-FAMILY: NSimSun; FONT-SIZE: 9pt; mso-bidi-font-family: NSimSun"><SPAN style="mso-spacerun: yes">&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp; </SPAN><SPAN style="COLOR: #2b91af">Console</SPAN>.WriteLine(<SPAN style="COLOR: #a31515">"{0}, {1}"</SPAN>, name, question);<o:p></o:p></SPAN></P>
<P style="LINE-HEIGHT: normal; MARGIN: 0in 0in 0pt; mso-layout-grid-align: none" class=MsoNormal><SPAN style="FONT-FAMILY: NSimSun; FONT-SIZE: 9pt; mso-bidi-font-family: NSimSun"><SPAN style="mso-spacerun: yes">&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp; </SPAN><SPAN style="COLOR: blue">return</SPAN> <SPAN style="COLOR: #2b91af">Console</SPAN>.ReadLine();<o:p></o:p></SPAN></P>
<P style="LINE-HEIGHT: normal; MARGIN: 0in 0in 0pt; mso-layout-grid-align: none" class=MsoNormal><SPAN style="FONT-FAMILY: NSimSun; FONT-SIZE: 9pt; mso-bidi-font-family: NSimSun"><SPAN style="mso-spacerun: yes">&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp; </SPAN><SPAN style="mso-spacerun: yes">&nbsp;</SPAN>}<o:p></o:p></SPAN></P>
<P style="MARGIN: 0in 0in 10pt" class=MsoCaption><STRONG><FONT color=#4f81bd><FONT face=Calibri><SPAN style="mso-spacerun: yes">&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp; </SPAN>Code <SPAN style="mso-no-proof: yes">1</SPAN><o:p></o:p></FONT></FONT></STRONG></P>
<P style="MARGIN: 0in 0in 10pt" class=MsoNormal><FONT size=3><FONT face=Calibri>As we learnt from the first programming class, functions/methods are basic execution unit for procedural languages and the basic mechanism to model data is arguments and variables:<o:p></o:p></FONT></FONT></P>
<P style="MARGIN: 0in 0in 10pt" class=MsoNormal><FONT size=3><FONT face=Calibri>Arguments are to model data flow in/out of a function, like “question” for method Prompt; variables are used to store states which could be shared among multiple statements, like “name” in method Prompt and “answer” in method Main; both arguments and variables are defined by name and type; arguments are always private to a method; variables are visible to the scope where they’re declared (the closest brace which enclose the declaration). <o:p></o:p></FONT></FONT></P>
<P style="MARGIN: 0in 0in 10pt" class=MsoNormal><FONT size=3><FONT face=Calibri>Not surprisingly, WF4 also chooses Argument and Variable to model data flow and internal states for Activities.<SPAN style="mso-spacerun: yes">&nbsp; </SPAN>And WF’s Arguments/Variables share a lot of those basic characteristics as their C# counterparts. So far the concept of arguments and variables seems to be very simple, now I need to touch something more subtle before talking about WF4’s implementations.<o:p></o:p></FONT></FONT></P>
<H1 style="MARGIN: 24pt 0in 0pt"><FONT size=5><FONT color=#365f91><FONT face=Cambria>Separation of data and program<o:p></o:p></FONT></FONT></FONT></H1>
<P style="MARGIN: 0in 0in 10pt" class=MsoNormal><FONT size=3><FONT face=Calibri></FONT></FONT>&nbsp;</P>
<P style="MARGIN: 0in 0in 10pt" class=MsoNormal><FONT size=3><FONT face=Calibri>Code1 only describes how to manipulate data like “question” and “name”, but doesn’t talk about where the data is stored. In my 32-bit machine with .Net 4.0, the C# code is compiled into this piece of X86 assembly code at runtime:<o:p></o:p></FONT></FONT></P>
<P style="LINE-HEIGHT: normal; MARGIN: 0in 0in 0pt 0.5in; mso-layout-grid-align: none" class=MsoNormal><SPAN style="FONT-FAMILY: NSimSun; COLOR: gray; FONT-SIZE: 9pt; mso-bidi-font-family: NSimSun">00000000<SPAN style="mso-spacerun: yes">&nbsp; </SPAN>push<SPAN style="mso-spacerun: yes">&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp; </SPAN>ebp <o:p></o:p></SPAN></P>
<P style="LINE-HEIGHT: normal; MARGIN: 0in 0in 0pt 0.5in; mso-layout-grid-align: none" class=MsoNormal><SPAN style="FONT-FAMILY: NSimSun; COLOR: gray; FONT-SIZE: 9pt; mso-bidi-font-family: NSimSun">00000001<SPAN style="mso-spacerun: yes">&nbsp; </SPAN>mov<SPAN style="mso-spacerun: yes">&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp; </SPAN>ebp,esp <o:p></o:p></SPAN></P>
<P style="LINE-HEIGHT: normal; MARGIN: 0in 0in 0pt 0.5in; mso-layout-grid-align: none" class=MsoNormal><SPAN style="FONT-FAMILY: NSimSun; COLOR: gray; FONT-SIZE: 9pt; mso-bidi-font-family: NSimSun">…<o:p></o:p></SPAN></P>
<P style="LINE-HEIGHT: normal; MARGIN: 0in 0in 0pt 0.5in; mso-layout-grid-align: none" class=MsoNormal><SPAN style="FONT-FAMILY: NSimSun; COLOR: green; FONT-SIZE: 9pt; mso-bidi-font-family: NSimSun">//copy argument “question”from register ecx to stack location [ebp-4]<o:p></o:p></SPAN></P>
<P style="LINE-HEIGHT: normal; MARGIN: 0in 0in 0pt 0.5in; mso-layout-grid-align: none" class=MsoNormal><SPAN style="FONT-FAMILY: NSimSun; COLOR: gray; FONT-SIZE: 9pt; mso-bidi-font-family: NSimSun">00000006<SPAN style="mso-spacerun: yes">&nbsp; </SPAN>mov<SPAN style="mso-spacerun: yes">&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp; </SPAN>dword ptr [ebp-4],ecx <o:p></o:p></SPAN></P>
<P style="LINE-HEIGHT: normal; MARGIN: 0in 0in 0pt 0.5in; mso-layout-grid-align: none" class=MsoNormal><SPAN style="FONT-FAMILY: NSimSun; COLOR: gray; FONT-SIZE: 9pt; mso-bidi-font-family: NSimSun">…<o:p></o:p></SPAN></P>
<P style="LINE-HEIGHT: normal; MARGIN: 0in 0in 0pt 0.5in; mso-layout-grid-align: none" class=MsoNormal><SPAN style="FONT-FAMILY: NSimSun; COLOR: green; FONT-SIZE: 9pt; mso-bidi-font-family: NSimSun">//call Console.ReadLine()</SPAN><SPAN style="FONT-FAMILY: NSimSun; COLOR: gray; FONT-SIZE: 9pt; mso-bidi-font-family: NSimSun"><o:p></o:p></SPAN></P>
<P style="LINE-HEIGHT: normal; MARGIN: 0in 0in 0pt 0.5in; mso-layout-grid-align: none" class=MsoNormal><SPAN style="FONT-FAMILY: NSimSun; COLOR: gray; FONT-SIZE: 9pt; mso-bidi-font-family: NSimSun">00000027<SPAN style="mso-spacerun: yes">&nbsp; </SPAN>call<SPAN style="mso-spacerun: yes">&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp; </SPAN>5053D5A0 <o:p></o:p></SPAN></P>
<P style="LINE-HEIGHT: normal; MARGIN: 0in 0in 0pt 0.5in; mso-layout-grid-align: none" class=MsoNormal><SPAN style="FONT-FAMILY: NSimSun; COLOR: green; FONT-SIZE: 9pt; mso-bidi-font-family: NSimSun">//copy return value of ReadLine from register eax to stack location [ebp-c] as variable “name”</SPAN><SPAN style="FONT-FAMILY: NSimSun; COLOR: gray; FONT-SIZE: 9pt; mso-bidi-font-family: NSimSun"><o:p></o:p></SPAN></P>
<P style="LINE-HEIGHT: normal; MARGIN: 0in 0in 0pt 0.5in; mso-layout-grid-align: none" class=MsoNormal><SPAN style="FONT-FAMILY: NSimSun; COLOR: gray; FONT-SIZE: 9pt; mso-bidi-font-family: NSimSun">0000002c<SPAN style="mso-spacerun: yes">&nbsp; </SPAN>mov<SPAN style="mso-spacerun: yes">&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp; </SPAN>dword ptr [ebp-0Ch],eax <o:p></o:p></SPAN></P>
<P style="LINE-HEIGHT: normal; MARGIN: 0in 0in 0pt 0.5in; mso-layout-grid-align: none" class=MsoNormal><SPAN style="FONT-FAMILY: NSimSun; COLOR: green; FONT-SIZE: 9pt; mso-bidi-font-family: NSimSun">//load argument “question”from stack location [ebp-4] and push it to stack <o:p></o:p></SPAN></P>
<P style="LINE-HEIGHT: normal; MARGIN: 0in 0in 0pt 0.5in; mso-layout-grid-align: none" class=MsoNormal><SPAN style="FONT-FAMILY: NSimSun; COLOR: green; FONT-SIZE: 9pt; mso-bidi-font-family: NSimSun">//as the 3<SUP>rd</SUP> argument to WriteLine method call <o:p></o:p></SPAN></P>
<P style="LINE-HEIGHT: normal; MARGIN: 0in 0in 0pt 0.5in; mso-layout-grid-align: none" class=MsoNormal><SPAN style="FONT-FAMILY: NSimSun; COLOR: gray; FONT-SIZE: 9pt; mso-bidi-font-family: NSimSun">00000035<SPAN style="mso-spacerun: yes">&nbsp; </SPAN>push<SPAN style="mso-spacerun: yes">&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp; </SPAN>dword ptr [ebp-4] <o:p></o:p></SPAN></P>
<P style="LINE-HEIGHT: normal; MARGIN: 0in 0in 0pt 0.5in; mso-layout-grid-align: none" class=MsoNormal><SPAN style="FONT-FAMILY: NSimSun; COLOR: green; FONT-SIZE: 9pt; mso-bidi-font-family: NSimSun">//load literal string “{0},{1}”from constant memory location to ecx <o:p></o:p></SPAN></P>
<P style="LINE-HEIGHT: normal; MARGIN: 0in 0in 0pt 0.5in; mso-layout-grid-align: none" class=MsoNormal><SPAN style="FONT-FAMILY: NSimSun; COLOR: green; FONT-SIZE: 9pt; mso-bidi-font-family: NSimSun">//as the 1<SUP>st</SUP> argument to WriteLine<o:p></o:p></SPAN></P>
<P style="LINE-HEIGHT: normal; MARGIN: 0in 0in 0pt 0.5in; mso-layout-grid-align: none" class=MsoNormal><SPAN style="FONT-FAMILY: NSimSun; COLOR: gray; FONT-SIZE: 9pt; mso-bidi-font-family: NSimSun">00000038<SPAN style="mso-spacerun: yes">&nbsp; </SPAN>mov<SPAN style="mso-spacerun: yes">&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp; </SPAN>ecx,dword ptr ds:[03292094h] <o:p></o:p></SPAN></P>
<P style="LINE-HEIGHT: normal; MARGIN: 0in 0in 0pt 0.5in; mso-layout-grid-align: none" class=MsoNormal><SPAN style="FONT-FAMILY: NSimSun; COLOR: green; FONT-SIZE: 9pt; mso-bidi-font-family: NSimSun">//load variable “name”from stack and store in edx as the 2<SUP>nd</SUP> argument to WriteLine</SPAN><SPAN style="FONT-FAMILY: NSimSun; COLOR: gray; FONT-SIZE: 9pt; mso-bidi-font-family: NSimSun"><o:p></o:p></SPAN></P>
<P style="LINE-HEIGHT: normal; MARGIN: 0in 0in 0pt 0.5in; mso-layout-grid-align: none" class=MsoNormal><SPAN style="FONT-FAMILY: NSimSun; COLOR: gray; FONT-SIZE: 9pt; mso-bidi-font-family: NSimSun">0000003e<SPAN style="mso-spacerun: yes">&nbsp; </SPAN>mov<SPAN style="mso-spacerun: yes">&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp; </SPAN>edx,dword ptr [ebp-8] <o:p></o:p></SPAN></P>
<P style="LINE-HEIGHT: normal; MARGIN: 0in 0in 0pt 0.5in; mso-layout-grid-align: none" class=MsoNormal><SPAN style="FONT-FAMILY: NSimSun; COLOR: green; FONT-SIZE: 9pt; mso-bidi-font-family: NSimSun">//call Console.WriteLine</SPAN><SPAN style="FONT-FAMILY: NSimSun; COLOR: gray; FONT-SIZE: 9pt; mso-bidi-font-family: NSimSun"><o:p></o:p></SPAN></P>
<P style="LINE-HEIGHT: normal; MARGIN: 0in 0in 0pt 0.5in; mso-layout-grid-align: none" class=MsoNormal><SPAN style="FONT-FAMILY: NSimSun; COLOR: gray; FONT-SIZE: 9pt; mso-bidi-font-family: NSimSun">00000041<SPAN style="mso-spacerun: yes">&nbsp; </SPAN>call<SPAN style="mso-spacerun: yes">&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp; </SPAN>5053DBE0 <o:p></o:p></SPAN></P>
<P style="LINE-HEIGHT: normal; MARGIN: 0in 0in 0pt 0.5in; mso-layout-grid-align: none" class=MsoNormal><SPAN style="FONT-FAMILY: NSimSun; COLOR: green; FONT-SIZE: 9pt; mso-bidi-font-family: NSimSun">…</SPAN><SPAN style="FONT-FAMILY: NSimSun; COLOR: gray; FONT-SIZE: 9pt; mso-bidi-font-family: NSimSun"> </SPAN><o:p></o:p></P>
<P style="MARGIN: 0in 0in 10pt 0.5in" class=MsoCaption><STRONG><FONT color=#4f81bd><FONT face=Calibri>Code <SPAN style="mso-no-proof: yes">2</SPAN><o:p></o:p></FONT></FONT></STRONG></P>
<P style="MARGIN: 0in 0in 10pt" class=MsoNormal><FONT size=3><FONT face=Calibri>As I annotated, variables and arguments are saved in stack or registers in a running process. The program does not know location of those variables at compile time, it just reference them with a relative address like “ebp-4 “ (an address&nbsp;calculated by&nbsp;subtracting 4 from value of register “ebp”).<SPAN style="mso-spacerun: yes">&nbsp; </SPAN>At runtime, register “ebp” will be populated with frame address for this method so variables will automatically be saved into the right place. Abstracting stack and register away, we could say arguments and variables are just names for some locations to a runtime environment; the program does not need to concern the real storage, it just needs to reference those names as if they were the real runtime data.<o:p></o:p></FONT></FONT></P>
<P style="MARGIN: 0in 0in 10pt" class=MsoNormal><FONT size=3><FONT face=Calibri><A title="Workflow internals" href="http://blogs.msdn.com/flow/archive/2010/02/21/workflow-foundation-internals-ii.aspx" mce_href="http://blogs.msdn.com/flow/archive/2010/02/21/workflow-foundation-internals-ii.aspx">As Andrew Au pointed out</A>, the design to separating program and data is basic yet critical to today’s programming systems. However, WF 3.X has an architecture where program and data are mixed together. For example, this is a simple activity defined in WF3.X model:<o:p></o:p></FONT></FONT></P>
<P style="LINE-HEIGHT: normal; MARGIN: 0in 0in 0pt; mso-layout-grid-align: none" class=MsoNormal><SPAN style="FONT-FAMILY: NSimSun; COLOR: blue; FONT-SIZE: 9pt; mso-bidi-font-family: NSimSun"><SPAN style="mso-spacerun: yes">&nbsp;&nbsp;&nbsp; </SPAN>public</SPAN><SPAN style="FONT-FAMILY: NSimSun; FONT-SIZE: 9pt; mso-bidi-font-family: NSimSun"> <SPAN style="COLOR: blue">class</SPAN> <SPAN style="COLOR: #2b91af">WriteLineActivity</SPAN> : <SPAN style="COLOR: #2b91af">SequenceActivity</SPAN><o:p></o:p></SPAN></P>
<P style="LINE-HEIGHT: normal; MARGIN: 0in 0in 0pt; mso-layout-grid-align: none" class=MsoNormal><SPAN style="FONT-FAMILY: NSimSun; FONT-SIZE: 9pt; mso-bidi-font-family: NSimSun"><SPAN style="mso-spacerun: yes">&nbsp;&nbsp;&nbsp; </SPAN>{<o:p></o:p></SPAN></P>
<P style="LINE-HEIGHT: normal; MARGIN: 0in 0in 0pt; mso-layout-grid-align: none" class=MsoNormal><SPAN style="FONT-FAMILY: NSimSun; FONT-SIZE: 9pt; mso-bidi-font-family: NSimSun"><SPAN style="mso-spacerun: yes">&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp; </SPAN><SPAN style="COLOR: blue">public</SPAN> <SPAN style="COLOR: blue">static</SPAN> <SPAN style="COLOR: #2b91af">DependencyProperty</SPAN> TextProperty = <SPAN style="COLOR: #2b91af">DependencyProperty</SPAN>.Register(<SPAN style="COLOR: #a31515">"Text"</SPAN>, <SPAN style="COLOR: blue">typeof</SPAN>(<SPAN style="COLOR: blue">string</SPAN>), <SPAN style="COLOR: blue">typeof</SPAN>(<SPAN style="COLOR: #2b91af">WriteLineActivity</SPAN>));<o:p></o:p></SPAN></P>
<P style="LINE-HEIGHT: normal; MARGIN: 0in 0in 0pt; mso-layout-grid-align: none" class=MsoNormal><SPAN style="FONT-FAMILY: NSimSun; FONT-SIZE: 9pt; mso-bidi-font-family: NSimSun"><o:p>&nbsp;</o:p></SPAN></P>
<P style="LINE-HEIGHT: normal; MARGIN: 0in 0in 0pt; mso-layout-grid-align: none" class=MsoNormal><SPAN style="FONT-FAMILY: NSimSun; FONT-SIZE: 9pt; mso-bidi-font-family: NSimSun"><SPAN style="mso-spacerun: yes">&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp; </SPAN><SPAN style="COLOR: blue">public</SPAN> <SPAN style="COLOR: blue">string</SPAN> Text<o:p></o:p></SPAN></P>
<P style="LINE-HEIGHT: normal; MARGIN: 0in 0in 0pt; mso-layout-grid-align: none" class=MsoNormal><SPAN style="FONT-FAMILY: NSimSun; FONT-SIZE: 9pt; mso-bidi-font-family: NSimSun"><SPAN style="mso-spacerun: yes">&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp; </SPAN>{<o:p></o:p></SPAN></P>
<P style="LINE-HEIGHT: normal; MARGIN: 0in 0in 0pt; mso-layout-grid-align: none" class=MsoNormal><SPAN style="FONT-FAMILY: NSimSun; FONT-SIZE: 9pt; mso-bidi-font-family: NSimSun"><SPAN style="mso-spacerun: yes">&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp; </SPAN><SPAN style="COLOR: blue">get</SPAN> { <SPAN style="COLOR: blue">return</SPAN> (<SPAN style="COLOR: blue">string</SPAN>)<SPAN style="COLOR: blue">base</SPAN>.GetValue(TextProperty); }<o:p></o:p></SPAN></P>
<P style="LINE-HEIGHT: normal; MARGIN: 0in 0in 0pt; mso-layout-grid-align: none" class=MsoNormal><SPAN style="FONT-FAMILY: NSimSun; FONT-SIZE: 9pt; mso-bidi-font-family: NSimSun"><SPAN style="mso-spacerun: yes">&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp; </SPAN><SPAN style="COLOR: blue">set</SPAN> { <SPAN style="COLOR: blue">base</SPAN>.SetValue(TextProperty, <SPAN style="COLOR: blue">value</SPAN>); }<o:p></o:p></SPAN></P>
<P style="LINE-HEIGHT: normal; MARGIN: 0in 0in 0pt; mso-layout-grid-align: none" class=MsoNormal><SPAN style="FONT-FAMILY: NSimSun; FONT-SIZE: 9pt; mso-bidi-font-family: NSimSun"><SPAN style="mso-spacerun: yes">&nbsp;&nbsp; </SPAN><SPAN style="mso-spacerun: yes">&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;</SPAN>}<o:p></o:p></SPAN></P>
<P style="LINE-HEIGHT: normal; MARGIN: 0in 0in 0pt; mso-layout-grid-align: none" class=MsoNormal><SPAN style="FONT-FAMILY: NSimSun; FONT-SIZE: 9pt; mso-bidi-font-family: NSimSun"><o:p>&nbsp;</o:p></SPAN></P>
<P style="LINE-HEIGHT: normal; MARGIN: 0in 0in 0pt; mso-layout-grid-align: none" class=MsoNormal><SPAN style="FONT-FAMILY: NSimSun; FONT-SIZE: 9pt; mso-bidi-font-family: NSimSun"><SPAN style="mso-spacerun: yes">&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp; </SPAN><SPAN style="COLOR: blue">protected</SPAN> <SPAN style="COLOR: blue">override</SPAN> <SPAN style="COLOR: #2b91af">ActivityExecutionStatus</SPAN> Execute(<SPAN style="COLOR: #2b91af">ActivityExecutionContext</SPAN> executionContext)<o:p></o:p></SPAN></P>
<P style="LINE-HEIGHT: normal; MARGIN: 0in 0in 0pt; mso-layout-grid-align: none" class=MsoNormal><SPAN style="FONT-FAMILY: NSimSun; FONT-SIZE: 9pt; mso-bidi-font-family: NSimSun"><SPAN style="mso-spacerun: yes">&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp; </SPAN>{<o:p></o:p></SPAN></P>
<P style="LINE-HEIGHT: normal; MARGIN: 0in 0in 0pt; mso-layout-grid-align: none" class=MsoNormal><SPAN style="FONT-FAMILY: NSimSun; FONT-SIZE: 9pt; mso-bidi-font-family: NSimSun"><SPAN style="mso-spacerun: yes">&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp; </SPAN><SPAN style="COLOR: #2b91af">Console</SPAN>.WriteLine(<SPAN style="COLOR: blue">this</SPAN>.Text);<o:p></o:p></SPAN></P>
<P style="LINE-HEIGHT: normal; MARGIN: 0in 0in 0pt; mso-layout-grid-align: none" class=MsoNormal><SPAN style="FONT-FAMILY: NSimSun; FONT-SIZE: 9pt; mso-bidi-font-family: NSimSun"><SPAN style="mso-spacerun: yes">&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp; </SPAN><SPAN style="COLOR: blue">return</SPAN> <SPAN style="COLOR: #2b91af">ActivityExecutionStatus</SPAN>.Closed;<o:p></o:p></SPAN></P>
<P style="LINE-HEIGHT: normal; MARGIN: 0in 0in 0pt; mso-layout-grid-align: none" class=MsoNormal><SPAN style="FONT-FAMILY: NSimSun; FONT-SIZE: 9pt; mso-bidi-font-family: NSimSun"><SPAN style="mso-spacerun: yes">&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp; </SPAN>}<o:p></o:p></SPAN></P>
<P style="LINE-HEIGHT: normal; MARGIN: 0in 0in 0pt; mso-layout-grid-align: none" class=MsoNormal><SPAN style="FONT-FAMILY: NSimSun; FONT-SIZE: 9pt; mso-bidi-font-family: NSimSun"><SPAN style="mso-spacerun: yes">&nbsp;&nbsp;&nbsp; </SPAN>}<o:p></o:p></SPAN></P>
<P style="MARGIN: 0in 0in 10pt" class=MsoCaption><STRONG><FONT color=#4f81bd><FONT face=Calibri><SPAN style="mso-spacerun: yes">&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp; </SPAN>Code <SPAN style="mso-no-proof: yes">3</SPAN><o:p></o:p></FONT></FONT></STRONG></P>
<P style="MARGIN: 0in 0in 10pt" class=MsoNormal><FONT face=Calibri><FONT size=3>The activity defines a property “Text” for its input. There are several problems with this design, including:<o:p></o:p></FONT></FONT></P>
<P style="TEXT-INDENT: -0.25in; MARGIN: 0in 0in 0pt 0.5in; mso-list: l0 level1 lfo1" class=MsoListParagraphCxSpFirst><SPAN style="FONT-FAMILY: Symbol; mso-bidi-font-family: Symbol; mso-fareast-font-family: Symbol"><SPAN style="mso-list: Ignore"><FONT size=3>·</FONT><SPAN style="FONT: 7pt 'Times New Roman'">&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp; </SPAN></SPAN></SPAN><FONT face=Calibri><FONT size=3>Data is stored in the program itself. A WriteLineActivity instance is not only execution logic for the activity, but also storage for the activity’s state. That means multiple running instances of the activity could not share the same WriteLineActivity object instance. Actually in WF3, a clone of WriteLineActivity object is created for every WhileActivity iteration and every ParallelActivity branch.<o:p></o:p></FONT></FONT></P>
<P style="TEXT-INDENT: -0.25in; MARGIN: 0in 0in 10pt 0.5in; mso-list: l0 level1 lfo1" class=MsoListParagraphCxSpLast><SPAN style="FONT-FAMILY: Symbol; mso-bidi-font-family: Symbol; mso-fareast-font-family: Symbol"><SPAN style="mso-list: Ignore"><FONT size=3>·</FONT><SPAN style="FONT: 7pt 'Times New Roman'">&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp; </SPAN></SPAN></SPAN><FONT size=3><FONT face=Calibri>There are no way to express intention and scope of the data. It’s hard for users of WriteLineActivity to reason whether “Text” is meant for input, output, or shared state for the activity’s own children. This of course leads to confusion and spaghetti code. Also, the runtime system has hard time to figure out data dependency between the Activities and sometimes could not even cleanup activities when it could otherwise.<o:p></o:p></FONT></FONT></P>
<P style="MARGIN: 0in 0in 10pt" class=MsoNormal><FONT size=3><FONT face=Calibri>In WF4, Activity data model is redesigned, and the number&nbsp;one goal is to create a separation between data and program.<o:p></o:p></FONT></FONT></P>
<H1 style="MARGIN: 24pt 0in 0pt"><FONT size=5><FONT color=#365f91><FONT face=Cambria>Workflow program, workflow instance, and ActivityContext<o:p></o:p></FONT></FONT></FONT></H1>
<P style="MARGIN: 0in 0in 10pt" class=MsoNormal><FONT size=3><FONT face=Calibri></FONT></FONT>&nbsp;</P>
<P style="MARGIN: 0in 0in 10pt" class=MsoNormal><FONT size=3><FONT face=Calibri>In previous section, we analyzed how a C# program code is detached from its running state. The key is to separate the concept of variable/argument as names and their real location at runtime. WF4 does exactly that. Here is a WF4 version of WriteLine:<o:p></o:p></FONT></FONT></P>
<P style="LINE-HEIGHT: normal; MARGIN: 0in 0in 0pt; mso-layout-grid-align: none" class=MsoNormal><SPAN style="FONT-FAMILY: NSimSun; COLOR: blue; FONT-SIZE: 9pt; mso-bidi-font-family: NSimSun"><SPAN style="mso-spacerun: yes">&nbsp;&nbsp;&nbsp; </SPAN>public</SPAN><SPAN style="FONT-FAMILY: NSimSun; FONT-SIZE: 9pt; mso-bidi-font-family: NSimSun"> <SPAN style="COLOR: blue">class</SPAN> <SPAN style="COLOR: #2b91af">MyWriteLine</SPAN> : <SPAN style="COLOR: #2b91af">CodeActivity</SPAN><o:p></o:p></SPAN></P>
<P style="LINE-HEIGHT: normal; MARGIN: 0in 0in 0pt; mso-layout-grid-align: none" class=MsoNormal><SPAN style="FONT-FAMILY: NSimSun; FONT-SIZE: 9pt; mso-bidi-font-family: NSimSun"><SPAN style="mso-spacerun: yes">&nbsp;&nbsp;&nbsp; </SPAN>{<o:p></o:p></SPAN></P>
<P style="LINE-HEIGHT: normal; MARGIN: 0in 0in 0pt; mso-layout-grid-align: none" class=MsoNormal><SPAN style="FONT-FAMILY: NSimSun; FONT-SIZE: 9pt; mso-bidi-font-family: NSimSun"><SPAN style="mso-spacerun: yes">&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp; </SPAN><SPAN style="COLOR: blue">public</SPAN> <SPAN style="COLOR: #2b91af">InArgument</SPAN>&lt;<SPAN style="COLOR: blue">string</SPAN>&gt; Text<o:p></o:p></SPAN></P>
<P style="LINE-HEIGHT: normal; MARGIN: 0in 0in 0pt; mso-layout-grid-align: none" class=MsoNormal><SPAN style="FONT-FAMILY: NSimSun; FONT-SIZE: 9pt; mso-bidi-font-family: NSimSun"><SPAN style="mso-spacerun: yes">&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp; </SPAN>{<o:p></o:p></SPAN></P>
<P style="LINE-HEIGHT: normal; MARGIN: 0in 0in 0pt; mso-layout-grid-align: none" class=MsoNormal><SPAN style="FONT-FAMILY: NSimSun; FONT-SIZE: 9pt; mso-bidi-font-family: NSimSun"><SPAN style="mso-spacerun: yes">&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp; </SPAN><SPAN style="COLOR: blue">get</SPAN>;<o:p></o:p></SPAN></P>
<P style="LINE-HEIGHT: normal; MARGIN: 0in 0in 0pt; mso-layout-grid-align: none" class=MsoNormal><SPAN style="FONT-FAMILY: NSimSun; FONT-SIZE: 9pt; mso-bidi-font-family: NSimSun"><SPAN style="mso-spacerun: yes">&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp; </SPAN><SPAN style="COLOR: blue">set</SPAN>;<o:p></o:p></SPAN></P>
<P style="LINE-HEIGHT: normal; MARGIN: 0in 0in 0pt; mso-layout-grid-align: none" class=MsoNormal><SPAN style="FONT-FAMILY: NSimSun; FONT-SIZE: 9pt; mso-bidi-font-family: NSimSun"><SPAN style="mso-spacerun: yes">&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp; </SPAN>}<o:p></o:p></SPAN></P>
<P style="LINE-HEIGHT: normal; MARGIN: 0in 0in 0pt; mso-layout-grid-align: none" class=MsoNormal><SPAN style="FONT-FAMILY: NSimSun; FONT-SIZE: 9pt; mso-bidi-font-family: NSimSun"><o:p>&nbsp;</o:p></SPAN></P>
<P style="LINE-HEIGHT: normal; MARGIN: 0in 0in 0pt; mso-layout-grid-align: none" class=MsoNormal><SPAN style="FONT-FAMILY: NSimSun; FONT-SIZE: 9pt; mso-bidi-font-family: NSimSun"><SPAN style="mso-spacerun: yes">&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp; </SPAN><SPAN style="COLOR: blue">protected</SPAN> <SPAN style="COLOR: blue">override</SPAN> <SPAN style="COLOR: blue">void</SPAN> Execute(<SPAN style="COLOR: #2b91af">CodeActivityContext</SPAN> context)<o:p></o:p></SPAN></P>
<P style="LINE-HEIGHT: normal; MARGIN: 0in 0in 0pt; mso-layout-grid-align: none" class=MsoNormal><SPAN style="FONT-FAMILY: NSimSun; FONT-SIZE: 9pt; mso-bidi-font-family: NSimSun"><SPAN style="mso-spacerun: yes">&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp; </SPAN>{<o:p></o:p></SPAN></P>
<P style="LINE-HEIGHT: normal; MARGIN: 0in 0in 0pt; mso-layout-grid-align: none" class=MsoNormal><SPAN style="FONT-FAMILY: NSimSun; FONT-SIZE: 9pt; mso-bidi-font-family: NSimSun"><SPAN style="mso-spacerun: yes">&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp; </SPAN><SPAN style="COLOR: blue">string</SPAN> text = <SPAN style="COLOR: blue">this</SPAN>.Text.Get(context);<o:p></o:p></SPAN></P>
<P style="LINE-HEIGHT: normal; MARGIN: 0in 0in 0pt; mso-layout-grid-align: none" class=MsoNormal><SPAN style="FONT-FAMILY: NSimSun; FONT-SIZE: 9pt; mso-bidi-font-family: NSimSun"><SPAN style="mso-spacerun: yes">&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp; </SPAN><SPAN style="COLOR: #2b91af">Console</SPAN>.WriteLine(text);<o:p></o:p></SPAN></P>
<P style="LINE-HEIGHT: normal; MARGIN: 0in 0in 0pt; mso-layout-grid-align: none" class=MsoNormal><SPAN style="FONT-FAMILY: NSimSun; FONT-SIZE: 9pt; mso-bidi-font-family: NSimSun"><SPAN style="mso-spacerun: yes">&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp; </SPAN>}<o:p></o:p></SPAN></P>
<P style="LINE-HEIGHT: normal; MARGIN: 0in 0in 0pt; mso-layout-grid-align: none" class=MsoNormal><SPAN style="FONT-FAMILY: NSimSun; FONT-SIZE: 9pt; mso-bidi-font-family: NSimSun"><SPAN style="mso-spacerun: yes">&nbsp;&nbsp;&nbsp; </SPAN>}<o:p></o:p></SPAN></P>
<P style="MARGIN: 0in 0in 10pt" class=MsoCaption><STRONG><FONT color=#4f81bd><FONT face=Calibri><SPAN style="mso-spacerun: yes">&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp; </SPAN>Code <SPAN style="mso-no-proof: yes">4</SPAN><o:p></o:p></FONT></FONT></STRONG></P>
<P style="MARGIN: 0in 0in 10pt" class=MsoNormal><FONT size=3><FONT face=Calibri>Arguments and variables are modeled by Argument and Variable classes. But the Argument class does not store the argument value itself, same as Variable. When the “Text” argument is defined on MyWriteLine, it only tells users that this Activity has a string input named “Text”, so that users could bind data to this name and the Activity itself could use this name in its internal expressions. But the real data is saved in an ActivityContext class. Every running workflow instance has its own ActivityContext just like every running method has its own frame in call stack. To access its runtime data, the activity needs to use Argument.Get(ActivityContext) to fetch the data out of the context. That way,&nbsp;different running instances could share the same&nbsp;MyWriteLine object instance&nbsp;yet have their own copy of runtime state.<o:p></o:p></FONT></FONT></P>
<P style="MARGIN: 0in 0in 10pt" class=MsoNormal><FONT size=3><FONT face=Calibri>With the separation of program and running instance, we often call an object instance of an Activity class a "Workflow program", similar to a copy of C# program in code. It’s a static description of&nbsp;logic detached with runtime environment; on the other hand, when the Activity object is scheduled by the WF runtime, it creates a "workflow instance", which is more of an abstract concept like the process for a C# program. It encapsulates the program’s runtime state. One WF program could have multiple running WF instances,&nbsp;similiar&nbsp;to relationship of&nbsp;C# program and processes. Workflow runtime use ActivityContext class to keep all states of a running WF instance. Through ActivityContext, an Activity could get its arguments and variables. <A title="Workflow Activity Model" href="http://blogs.msdn.com/flow/archive/2010/01/24/lights-camera-activities-windows-workflow-foundation-s-activity-model.aspx" mce_href="http://blogs.msdn.com/flow/archive/2010/01/24/lights-camera-activities-windows-workflow-foundation-s-activity-model.aspx">As we introduced previously</A>, there are different flavor of Activity modeling style with different Activity base classes. Accordingly, WF has defined different flavor of ActivityContext classes which expose different level of runtime functionalities.</FONT></FONT></P>
<P style="MARGIN: 0in 0in 10pt" class=MsoNormal><FONT size=3><FONT face=Calibri></FONT></FONT>&nbsp;</P>
<P style="MARGIN: 0in 0in 10pt" class=MsoNormal><FONT size=3><FONT face=Calibri>&nbsp;</FONT></FONT><FONT size=3><FONT face=Calibri><A title="Workflow Activity Argument" href="http://blogs.msdn.com/flow/archive/2010/04/06/workflow-foundation-4-0-activity-data-model-ii.aspx" mce_href="http://blogs.msdn.com/flow/archive/2010/04/06/workflow-foundation-4-0-activity-data-model-ii.aspx">To be continued...</A></FONT></FONT></P>
<P style="MARGIN: 0in 0in 10pt" class=MsoNormal><FONT size=3><FONT face=Calibri></FONT></FONT>&nbsp;</P>
<P style="MARGIN: 0in 0in 10pt" class=MsoNormal><FONT size=3><FONT face=Calibri>Yun Jin<BR>Development Lead<BR><A href="http://blogs.msdn.com/yunjin">http://blogs.msdn.com/yunjin</A></FONT></FONT><FONT size=3><FONT face=Calibri><o:p></o:p></FONT></FONT></P>]]></content:encoded>
    </item>
    <item>
      <title>Workflow Foundation Internals (III)</title>
      <link>https://docs.microsoft.com/archive/blogs/flow/workflow-foundation-internals-iii</link>
      <pubDate>Sat, 20 Feb 2010 20:45:00 GMT</pubDate>
      <dc:creator><![CDATA[andrewau]]></dc:creator>
      <guid
        isPermaLink="false">https://blogs.msdn.microsoft.com/flow/2010/02/20/workflow-foundation-internals-iii/</guid>
      <description><![CDATA[Workflow Foundation Internals (III)
Andrew Au
Continue with our last article, we will work on...]]></description>
      <content:encoded><![CDATA[<P><B>Workflow Foundation Internals (III)</B></P>
<P><B>Andrew Au</B></P>
<P>Continue with our last article, we will work on allowing parallelism and create the workflow/host communication pattern. This pattern is actually very common, such as waiting for multiple approvers to approve a document. Last time we notice the problem is that ScheduleActivity can only be called once, so the most obvious solution is to allow multiple delegates to be put in the states. Looking at states.Frames, it is a stack and we access the top of the stack anytime. With parallelism, we want to have a stack like data structure with multiple tops. Think about it, this is really just a rooted tree. In our data structure, we will keep all the leaves and have parent pointers for the parent frames. With multiple tops, activity execution with a pointer to the set of all states will not work, because the activity doesn’t know which frame it is in. We changed the delegate from Action&lt;State&gt; to Action&lt;Frame&gt; and the rest will become obvious.</P>
<P><I><A href="https://msdnshared.blob.core.windows.net/media/TNBlogsFS/BlogFileStorage/blogs_msdn/flow/WindowsLiveWriter/WorkflowFoundationInternalsIII_B36F/7-to-8_2.png" original-url="http://blogs.msdn.com/blogfiles/flow/WindowsLiveWriter/WorkflowFoundationInternalsIII_B36F/7-to-8_2.png" mce_href="http://blogs.msdn.com/blogfiles/flow/WindowsLiveWriter/WorkflowFoundationInternalsIII_B36F/7-to-8_2.png"><IMG title=7-to-8 style="BORDER-RIGHT: 0px; BORDER-TOP: 0px; DISPLAY: block; FLOAT: none; MARGIN-LEFT: auto; BORDER-LEFT: 0px; MARGIN-RIGHT: auto; BORDER-BOTTOM: 0px" height=613 alt=7-to-8 src="https://msdnshared.blob.core.windows.net/media/TNBlogsFS/BlogFileStorage/blogs_msdn/flow/WindowsLiveWriter/WorkflowFoundationInternalsIII_B36F/7-to-8_thumb.png" original-url="http://blogs.msdn.com/blogfiles/flow/WindowsLiveWriter/WorkflowFoundationInternalsIII_B36F/7-to-8_thumb.png" width=948 border=0 mce_src="http://blogs.msdn.com/blogfiles/flow/WindowsLiveWriter/WorkflowFoundationInternalsIII_B36F/7-to-8_thumb.png"></A> Code Sample: Version 8</I></P>
<P>We are using the old activities because we want to keep safe. No parallelism feature is used in the last sample, we will now introduce parallelism. Parallel is the simplest activity out of the box and we will use parallel to schedule two Reads. </P>
<P><I><A href="https://msdnshared.blob.core.windows.net/media/TNBlogsFS/BlogFileStorage/blogs_msdn/flow/WindowsLiveWriter/WorkflowFoundationInternalsIII_B36F/8-to-9_2.png" original-url="http://blogs.msdn.com/blogfiles/flow/WindowsLiveWriter/WorkflowFoundationInternalsIII_B36F/8-to-9_2.png" mce_href="http://blogs.msdn.com/blogfiles/flow/WindowsLiveWriter/WorkflowFoundationInternalsIII_B36F/8-to-9_2.png"><IMG title=8-to-9 style="BORDER-RIGHT: 0px; BORDER-TOP: 0px; DISPLAY: block; FLOAT: none; MARGIN-LEFT: auto; BORDER-LEFT: 0px; MARGIN-RIGHT: auto; BORDER-BOTTOM: 0px" height=690 alt=8-to-9 src="https://msdnshared.blob.core.windows.net/media/TNBlogsFS/BlogFileStorage/blogs_msdn/flow/WindowsLiveWriter/WorkflowFoundationInternalsIII_B36F/8-to-9_thumb.png" original-url="http://blogs.msdn.com/blogfiles/flow/WindowsLiveWriter/WorkflowFoundationInternalsIII_B36F/8-to-9_thumb.png" width=948 border=0 mce_src="http://blogs.msdn.com/blogfiles/flow/WindowsLiveWriter/WorkflowFoundationInternalsIII_B36F/8-to-9_thumb.png"></A>&nbsp;</I><I>Code Sample: Version 9</I></P>
<P>Notice the sequential execution of the work despite of the use of Parallel activity. Parallel activity essentially allows multiple outstanding works. When these work items are waiting for external signals, then these external signals are all waiting together. We used frame as dependencies for delegates, but sometimes delegates are not ready for execution not because of control dependencies, but data dependencies. These data eventually come from the host. From states, we can signal the host to wait for these data, and from the host, those dependencies could be broken when the data is ready. WF3 provided this mechanism though WorkflowQueue, and WF4 provided this through Bookmarks. Queue is sometimes overkill when the program really just request one item.</P>
<P><I><A href="https://msdnshared.blob.core.windows.net/media/TNBlogsFS/BlogFileStorage/blogs_msdn/flow/WindowsLiveWriter/WorkflowFoundationInternalsIII_B36F/9-to-10_2.png" original-url="http://blogs.msdn.com/blogfiles/flow/WindowsLiveWriter/WorkflowFoundationInternalsIII_B36F/9-to-10_2.png" mce_href="http://blogs.msdn.com/blogfiles/flow/WindowsLiveWriter/WorkflowFoundationInternalsIII_B36F/9-to-10_2.png"><IMG title=9-to-10 style="BORDER-RIGHT: 0px; BORDER-TOP: 0px; DISPLAY: block; FLOAT: none; MARGIN-LEFT: auto; BORDER-LEFT: 0px; MARGIN-RIGHT: auto; BORDER-BOTTOM: 0px" height=683 alt=9-to-10 src="https://msdnshared.blob.core.windows.net/media/TNBlogsFS/BlogFileStorage/blogs_msdn/flow/WindowsLiveWriter/WorkflowFoundationInternalsIII_B36F/9-to-10_thumb.png" original-url="http://blogs.msdn.com/blogfiles/flow/WindowsLiveWriter/WorkflowFoundationInternalsIII_B36F/9-to-10_thumb.png" width=1026 border=0 mce_src="http://blogs.msdn.com/blogfiles/flow/WindowsLiveWriter/WorkflowFoundationInternalsIII_B36F/9-to-10_thumb.png"></A> Code Sample: Version 10</I></P>
<P>This will be the end of our home made WF series, certainly we still have a long way to go until we get what will have today for workflow foundation. But I guess up to now you should able to appreciate what WF brings to you and how to best leverage WF for your application.</P>
<p><a href="https://msdnshared.blob.core.windows.net/media/MSDNBlogsFS/prod.evol.blogs.msdn.com/CommunityServer.Components.PostAttachments/00/09/96/69/65/HomeMadeWF.zip" original-url="http://blogs.msdn.com/cfs-file.ashx/__key/communityserver-components-postattachments/00-09-96-69-65/HomeMadeWF.zip">HomeMadeWF.zip</a></p>]]></content:encoded>
    </item>
    <item>
      <title>Workflow Foundation Internals (II)</title>
      <link>https://docs.microsoft.com/archive/blogs/flow/workflow-foundation-internals-ii</link>
      <pubDate>Sat, 20 Feb 2010 20:39:00 GMT</pubDate>
      <dc:creator><![CDATA[andrewau]]></dc:creator>
      <guid
        isPermaLink="false">https://blogs.msdn.microsoft.com/flow/2010/02/20/workflow-foundation-internals-ii/</guid>
      <description><![CDATA[Workflow Foundation Internals (II)
Andrew Au
Continue with our last article, we will work on...]]></description>
      <content:encoded><![CDATA[<P><B>Workflow Foundation Internals (II)</B></P>
<P><B>Andrew Au</B></P>
<P>Continue with our last article, we will work on separating program and data. Program and data are very distinct concepts from the perspective of a programmer. For example, you can run code, but you can’t run data. Code are not expected to be changed during runtime (except some circumstances such as hook or overlay), but data are expected to be changed all the time. From the processor’s perspective, they are no different. They are just some bytes. From an operating system perspective, the fact that code is read only allow optimization of main memory usage, because a single copy of the code can be used to run multiple processes.</P>
<P>Exactly the same argument applies for workflow. We think of Sequence as the program, but then sequenceCounter is just execution data. The fact that sequenceCounter is defined on the Sequence class made them inseparable. Consider multiple workflows are running on the same definition, the sequenceCounter will mix up and cause problem.</P>
<P>Reading the code for Activity, the fact that States is defined on the workflow is an even bigger problem. Instead of having them accessible from the activity as a protected field, we will retrieve it from the parameter of the Execute method. Similarly, we should not allow NextDelegate to be defined on the activity as well. This one is getting more complicated, as Sequence execution will require storage of two delegate objects. To solve this problem, we will use a Stack&lt;Frame&gt; holder for these objects. Diligent readers are recommended to perform the exercise himself, because we are going to take a quantum leap (instead of small refactorings) to move to the next version as shown below</P>
<P><I><A href="https://msdnshared.blob.core.windows.net/media/TNBlogsFS/BlogFileStorage/blogs_msdn/flow/WindowsLiveWriter/WorkflowFoundationInternalsII_B209/5-to-6_2.png" original-url="http://blogs.msdn.com/blogfiles/flow/WindowsLiveWriter/WorkflowFoundationInternalsII_B209/5-to-6_2.png" mce_href="http://blogs.msdn.com/blogfiles/flow/WindowsLiveWriter/WorkflowFoundationInternalsII_B209/5-to-6_2.png"><IMG title=5-to-6 style="BORDER-RIGHT: 0px; BORDER-TOP: 0px; DISPLAY: block; FLOAT: none; MARGIN-LEFT: auto; BORDER-LEFT: 0px; MARGIN-RIGHT: auto; BORDER-BOTTOM: 0px" height=573 alt=5-to-6 src="https://msdnshared.blob.core.windows.net/media/TNBlogsFS/BlogFileStorage/blogs_msdn/flow/WindowsLiveWriter/WorkflowFoundationInternalsII_B209/5-to-6_thumb.png" original-url="http://blogs.msdn.com/blogfiles/flow/WindowsLiveWriter/WorkflowFoundationInternalsII_B209/5-to-6_thumb.png" width=975 border=0 mce_src="http://blogs.msdn.com/blogfiles/flow/WindowsLiveWriter/WorkflowFoundationInternalsII_B209/5-to-6_thumb.png"></A> Code Sample: Version 6</I></P>
<P>I tried to keep modification of Version 6 from Version 5 as small as possible. As we are moving the delegate storage from the activity to state, we also optimized Sequence execution. For now, executing a particular activity will not pass through sequence, but rather just saving the continuation of the sequence in the stack. Given the code is good now, I will refactor. In particular, we will move more logic into States so that the stack is maintained by state instead of being distributed in Sequence and Program. Making Frames a private field drives all these refactorings. All I did is really just giving the right name to the set of operations I did to the states.</P>
<P><I>Version 7 has no structural change, just encapsulation of the stack.</I></P>
<P><I>Code Sample: Version 7</I></P>
<P>We are getting very close now. For we are now serializing the state object, we should have completed the separation? The answer is NO. This is because the states contain a reference to the delegates, and then the delegates will link back to the program. To break this link, we cannot serialize the delegate anymore. We will serialize the MethodInfo and the activity ID as well, where activity ID can be obtained from a traversal of the activity tree. We will skip this part as this complicates our sample. Another problem is that the program is not constrained to be read only. There are multiple ways of solving it. WF3 chooses to make a copy of the program and always run the copy, while WF4 chooses to make a copy of the program (parts that is important to the runtime) and verify the main program is not modified at runtime. We could have also done by making user fail when program is changed at runtime as well. Again, this complicates the sample and we will stop our discussion here. Trying to implement or reading the existing implementation is a good way to appreciate this.</P>
<P>Another big problem with program and data is that a program line can be executed multiple times in a process. The simplest example is a loop. Those data has to be stored on the frame instead of the state. In fact, all states should be stored on a frame. Storing on States itself make them global variables. With frames, we can control variable scoping. This is one big improvement over the last version of WF.</P>
<P>Look at the implementation of States. One problem is ScheduleActivity can only be called once, because calling a subsequent call to ScheduleActivity will overwrite the NextDelegate field. In this next post, I will talk improve ScheduleActivity to allow multiple outstanding activities, and workflow-host communication through Bookmarks.</P>
<p><a href="https://msdnshared.blob.core.windows.net/media/MSDNBlogsFS/prod.evol.blogs.msdn.com/CommunityServer.Components.PostAttachments/00/09/96/69/62/HomeMadeWF.zip" original-url="http://blogs.msdn.com/cfs-file.ashx/__key/communityserver-components-postattachments/00-09-96-69-62/HomeMadeWF.zip">HomeMadeWF.zip</a></p>]]></content:encoded>
    </item>
    <item>
      <title>Workflow Foundation Internals (I)</title>
      <link>https://docs.microsoft.com/archive/blogs/flow/workflow-foundation-internals-i</link>
      <pubDate>Sat, 20 Feb 2010 20:36:00 GMT</pubDate>
      <dc:creator><![CDATA[andrewau]]></dc:creator>
      <guid
        isPermaLink="false">https://blogs.msdn.microsoft.com/flow/2010/02/20/workflow-foundation-internals-i/</guid>
      <description><![CDATA[Workflow Foundation Internals (I)
Andrew Au
Inspired by the book Essential Windows Workflow...]]></description>
      <content:encoded><![CDATA[<P><B>Workflow Foundation Internals (I)</B></P>
<P><B>Andrew Au</B></P>
<P>Inspired by the book <A href="http://www.amazon.com/Essential-Windows-Workflow-Foundation-Dharma/dp/0321399838" mce_href="http://www.amazon.com/Essential-Windows-Workflow-Foundation-Dharma/dp/0321399838">Essential Windows Workflow Foundation</A> that describes the last version of Workflow Foundation, I can’t stop myself trying to write an equivalent piece for WF4. While the basic working principle is fundamentally the same, the programming model is quite different. We will start from the same principle of using serialization of delegate, and we will develop our ‘home-made’ workflow runtime, and we will see how WF4 made its design decisions.</P>
<P>First of all, let’s review the underlying CLR technology for continuation. Continuation is a point that can be saved for resuming execution, and therefore it needs to contain pointer to executable code. Delegate is used for this purpose. The great thing about delegate can be round-tripped to a binary store and back remain executable. Here is a code sample to show the roundtrip of that delegate works. </P>
<P><I>Code Sample 1: SerializableDelegate</I></P>
<P>Serializable delegate provided us with a mechanism to suspend a running managed thread, and resume in another process (perhaps on another machine). Doing so has a lot of advantages. The most important one is that we remove the ‘affinities’. The code is no longer stuck to original process or even the original machine. This allows us to scale the application by simply adding more machines. Moreover, we now have control. For example, we could delete the serialized delegate instead of resuming it. By doing so, we essentially canceled the execution. Similarly, we could suspend the execution for days without worrying main memory are being used. Let us take a look at this code sample to see how serializable delegate allow us to break a program into several processes.</P>
<P><I>Code Sample: Version 1</I></P>
<P>Run the program three times, you will see “Hello world to homemade workflow foundation!” is displayed on the console. With the code above, we have just engineered our first most primitive workflow application using the code above. Needless to say, this is rough and there are a lot of things we can improve upon. We will take our first step to separate the concern of scalability (i.e. the fact that we are serializing delegates from the business logic). For that, we create a new class named ReadReadWrite, move the business logic method there, and that leads us to the version 2. </P>
<P><I><A href="https://msdnshared.blob.core.windows.net/media/TNBlogsFS/BlogFileStorage/blogs_msdn/flow/WindowsLiveWriter/WorkflowFoundationInternalsI_AF34/1-to-2_2.png" original-url="http://blogs.msdn.com/blogfiles/flow/WindowsLiveWriter/WorkflowFoundationInternalsI_AF34/1-to-2_2.png" mce_href="http://blogs.msdn.com/blogfiles/flow/WindowsLiveWriter/WorkflowFoundationInternalsI_AF34/1-to-2_2.png"><IMG style="BORDER-RIGHT-WIDTH: 0px; DISPLAY: block; FLOAT: none; BORDER-TOP-WIDTH: 0px; BORDER-BOTTOM-WIDTH: 0px; MARGIN-LEFT: auto; BORDER-LEFT-WIDTH: 0px; MARGIN-RIGHT: auto" title=1-to-2 border=0 alt=1-to-2 src="https://msdnshared.blob.core.windows.net/media/TNBlogsFS/BlogFileStorage/blogs_msdn/flow/WindowsLiveWriter/WorkflowFoundationInternalsI_AF34/1-to-2_thumb.png" original-url="http://blogs.msdn.com/blogfiles/flow/WindowsLiveWriter/WorkflowFoundationInternalsI_AF34/1-to-2_thumb.png" width=604 height=262 mce_src="http://blogs.msdn.com/blogfiles/flow/WindowsLiveWriter/WorkflowFoundationInternalsI_AF34/1-to-2_thumb.png"></A> </I></P>
<P><I>Code Sample: Version 2</I></P>
<P>First, I put a while loop in the main program to avoid run the program three times. This is really just for convenience. It is good enough for us to know we CAN break them into different processes, but we don’t have to. The refactoring is mostly straightforward, but there is one thing that worth notice here. I made NextDelegate a property of ReadReadWrite. This is to allow all delegates to share a uniform signature. </P>
<P>The hosting program and the business logic are separated now. At this point, we have the still got two coupling between the host and the business logic. The host need to know the starting point is RunStep1, and the host need to know NextDelegate is the property storing the continuation. These coupling make the host not a generic one. We could remove these coupling by having a base class for ReadReadWrite. Let’s call it Activity.</P>
<P><I></I></P>
<P><I><A href="https://msdnshared.blob.core.windows.net/media/TNBlogsFS/BlogFileStorage/blogs_msdn/flow/WindowsLiveWriter/WorkflowFoundationInternalsI_AF34/2-to-3_2.png" original-url="http://blogs.msdn.com/blogfiles/flow/WindowsLiveWriter/WorkflowFoundationInternalsI_AF34/2-to-3_2.png" mce_href="http://blogs.msdn.com/blogfiles/flow/WindowsLiveWriter/WorkflowFoundationInternalsI_AF34/2-to-3_2.png"><IMG style="BORDER-RIGHT-WIDTH: 0px; DISPLAY: block; FLOAT: none; BORDER-TOP-WIDTH: 0px; BORDER-BOTTOM-WIDTH: 0px; MARGIN-LEFT: auto; BORDER-LEFT-WIDTH: 0px; MARGIN-RIGHT: auto" title=2-to-3 border=0 alt=2-to-3 src="https://msdnshared.blob.core.windows.net/media/TNBlogsFS/BlogFileStorage/blogs_msdn/flow/WindowsLiveWriter/WorkflowFoundationInternalsI_AF34/2-to-3_thumb.png" original-url="http://blogs.msdn.com/blogfiles/flow/WindowsLiveWriter/WorkflowFoundationInternalsI_AF34/2-to-3_thumb.png" width=604 height=454 mce_src="http://blogs.msdn.com/blogfiles/flow/WindowsLiveWriter/WorkflowFoundationInternalsI_AF34/2-to-3_thumb.png"></A> Code Sample: Version 3</I></P>
<P>The refactoring is straightforward. Looking at ReadReadWrite, the code is now pretty easy to write. One thing that we don’t like is that the Execute method and the RunStep2 method are essentially the same piece of logic to read a file, it is best to share the logic into reusable components. To tackle this problem, we realize there are really two hurdles. One is that they update different states, and that they return different delegates. The fact that they are returning different delegate is a problem, because these delegates are really control logic, and is orthogonal to reading a file. We made them together and therefore the logic not cohesive. Now we further optimize the structure by separating them.</P>
<P><I><A href="https://msdnshared.blob.core.windows.net/media/TNBlogsFS/BlogFileStorage/blogs_msdn/flow/WindowsLiveWriter/WorkflowFoundationInternalsI_AF34/3-to-4_2.png" original-url="http://blogs.msdn.com/blogfiles/flow/WindowsLiveWriter/WorkflowFoundationInternalsI_AF34/3-to-4_2.png" mce_href="http://blogs.msdn.com/blogfiles/flow/WindowsLiveWriter/WorkflowFoundationInternalsI_AF34/3-to-4_2.png"><IMG style="BORDER-RIGHT-WIDTH: 0px; DISPLAY: block; FLOAT: none; BORDER-TOP-WIDTH: 0px; BORDER-BOTTOM-WIDTH: 0px; MARGIN-LEFT: auto; BORDER-LEFT-WIDTH: 0px; MARGIN-RIGHT: auto" title=3-to-4 border=0 alt=3-to-4 src="https://msdnshared.blob.core.windows.net/media/TNBlogsFS/BlogFileStorage/blogs_msdn/flow/WindowsLiveWriter/WorkflowFoundationInternalsI_AF34/3-to-4_thumb.png" original-url="http://blogs.msdn.com/blogfiles/flow/WindowsLiveWriter/WorkflowFoundationInternalsI_AF34/3-to-4_thumb.png" width=713 height=573 mce_src="http://blogs.msdn.com/blogfiles/flow/WindowsLiveWriter/WorkflowFoundationInternalsI_AF34/3-to-4_thumb.png"></A> </I></P>
<P><I>Code Sample: Version 4</I></P>
<P>It is non-trivial to write the Sequence activity, and it is far from optimal for now. We will postpone the discussion of optimizing Sequence to the next post. For now I want to focus on removing the duplication of Read1 and Read2. With the code above, Read1 and Read2 are really just reading file now. The last step to merge these two classes together is to make them access the state by name instead of a static field reference.</P>
<P><I><A href="https://msdnshared.blob.core.windows.net/media/TNBlogsFS/BlogFileStorage/blogs_msdn/flow/WindowsLiveWriter/WorkflowFoundationInternalsI_AF34/4-to-5_2.png" original-url="http://blogs.msdn.com/blogfiles/flow/WindowsLiveWriter/WorkflowFoundationInternalsI_AF34/4-to-5_2.png" mce_href="http://blogs.msdn.com/blogfiles/flow/WindowsLiveWriter/WorkflowFoundationInternalsI_AF34/4-to-5_2.png"><IMG style="BORDER-RIGHT-WIDTH: 0px; DISPLAY: block; FLOAT: none; BORDER-TOP-WIDTH: 0px; BORDER-BOTTOM-WIDTH: 0px; MARGIN-LEFT: auto; BORDER-LEFT-WIDTH: 0px; MARGIN-RIGHT: auto" title=4-to-5 border=0 alt=4-to-5 src="https://msdnshared.blob.core.windows.net/media/TNBlogsFS/BlogFileStorage/blogs_msdn/flow/WindowsLiveWriter/WorkflowFoundationInternalsI_AF34/4-to-5_thumb.png" original-url="http://blogs.msdn.com/blogfiles/flow/WindowsLiveWriter/WorkflowFoundationInternalsI_AF34/4-to-5_thumb.png" width=961 height=574 mce_src="http://blogs.msdn.com/blogfiles/flow/WindowsLiveWriter/WorkflowFoundationInternalsI_AF34/4-to-5_thumb.png"></A> </I></P>
<P><I>Code Sample: Version 5</I></P>
<P>Now we have reached a state where we can write reusable activity. These activities don’t have to concern themselves with the serialization. Without reading the code of Main, one does not even know serialization is happening. Looking at Read or Write, does it look like our activities API? In the next post of this series, we will continue to work on this example and show why there is a parameter to the Execute method, and how that separates program from data.</P>
<p><a href="https://msdnshared.blob.core.windows.net/media/MSDNBlogsFS/prod.evol.blogs.msdn.com/CommunityServer.Components.PostAttachments/00/09/96/69/60/HomeMadeWF.zip" original-url="http://blogs.msdn.com/cfs-file.ashx/__key/communityserver-components-postattachments/00-09-96-69-60/HomeMadeWF.zip">HomeMadeWF.zip</a></p>]]></content:encoded>
    </item>
  </channel>
</rss>