技术开发 频道

详解Visual Studio中的移植设计器功能

  【IT168 技术文档】如果你想建一个像PrePostSequence 那样的自定义活动,而使用者没有Visual Studio来使用它怎么办?此外,很多产品允许终端客户自定义工作流。为了解决这个问题,微软的新一代工作流提供了方便移植设计器的功能。在这个练习中,你可以看到移植设计器所需要的代码,并且体验下移植后的设计器。

  1.打开解决方案

  你可以使用练习9完成后的那个解决方案,经过一些操作,自己完成设计器移植。由于时间的限制,我们将直接打开设计器移植后的解决方案,看一下用来完成这些工作的代码。

  (1)打开微软Visual Studio 2010.

  (2)从以下路径打开解决方案: %TrainingKitInstallFolder%\Labs\ IntroToWF\Ex10-HostedDesigner\End.

  (3)按CTRL+SHIFT+B来编译解决方案.

  2.浏览HelloDesigner解决方案

  HelloDesigner是一个WPF项目。

  (1)展开HelloDesigner的被引用程序集。你可以看到为了移植设计器,这个项目主要引用了以下程序集:

  ? System.Activities.Presentation

  ·System.Activities.Core.Presentation

  ·System.Activities

  ·HelloWorkflow.Activities

  ·HelloWorkflow.Activities.Designers

  (2)双击MainWindow.xaml文件,你可以看到用来描述移植设计器用户界面的WPF xaml代码。如以下的代码段所示。

  (代码段 - Introduction to WF4 Lab – MainWindow XAML CSharp)

<Window x:Class="HelloDesigner.MainWindow"
        xmlns
="http://schemas.microsoft.com/winfx/2006/xaml/presentation"
        xmlns:x
="http://schemas.microsoft.com/winfx/2006/xaml"
        Title
="MainWindow" Height="600" Width="1000">
    
<Grid>
        
<Grid.RowDefinitions>
            
<RowDefinition Height="4*" />
            
<RowDefinition Height="*" />
        
</Grid.RowDefinitions>
        
<Grid Name="grid1">
            
<Grid.ColumnDefinitions>
                
<ColumnDefinition Width="Auto" />
                
<ColumnDefinition Width="4*" />
                
<ColumnDefinition Width="Auto" />
            
</Grid.ColumnDefinitions>
        
</Grid>
        
<TextBox Grid.Row="1" Name="textXAML"    
                 VerticalScrollBarVisibility
="Visible" />
    
</Grid>
</Window>

   (代码段 - Introduction to WF4 Lab – MainWindow XAML VB)

<Window x:Class="MainWindow"
        xmlns
="http://schemas.microsoft.com/winfx/2006/xaml/presentation"
        xmlns:x
="http://schemas.microsoft.com/winfx/2006/xaml"
        Title
="MainWindow" Height="600" Width="1000">
    
<Grid>
        
<Grid.RowDefinitions>
            
<RowDefinition Height="4*" />
            
<RowDefinition Height="*" />
        
</Grid.RowDefinitions>
        
<Grid Name="grid1">
            
<Grid.ColumnDefinitions>
                
<ColumnDefinition Width="Auto" />
                
<ColumnDefinition Width="4*" />
                
<ColumnDefinition Width="Auto" />
            
</Grid.ColumnDefinitions>
        
</Grid>
        
<TextBox Grid.Row="1" Name="textXAML"
                 VerticalScrollBarVisibility
="Visible" />
    
</Grid>
</Window>

   (3)打开MainWindow.xaml.cs (C#) 或者MainWindow.xaml.vb,你可以看到用来实现移植设计器的源代码。

  如下面所示, RegisterMetadata函数 使得设计器能够储存元数据。

  (代码段- Introduction to WF4 Lab – RegisterMetadata method CSharp)

private void RegisterMetadata()
{
    DesignerMetadata metaData
= new DesignerMetadata();
    metaData.Register();
    AttributeTableBuilder builder
= new AttributeTableBuilder();
    MetadataStore.AddAttributeTable(builder.CreateTable());
}

 

  (代码段- Introduction to WF4 Lab – RegisterMetadata method VB)

Public Sub RegisterMetadata()
    
Dim metaData As DesignerMetadata = New DesignerMetadata()
    metaData.Register()
    
Dim builder As AttributeTableBuilder = New AttributeTableBuilder()
    MetadataStore.AddAttributeTable(builder.CreateTable())
End Sub

  当你移植设计器,你可以控制工具栏。你可以选择出现在工具栏上的控件,该控件的分类,甚至控件的名称。如下面所示,CreateToolboxControl函数实现了上述功能。

  (代码段- Introduction to WF4 Lab – CreateToolboxControl method CSharp)

private ToolboxControl CreateToolboxControl()
{
    
//Create the ToolBoxControl
    ToolboxControl ctrl = new ToolboxControl();

    
//Create a collection of category items
    ToolboxCategory category = new ToolboxCategory("Hello Workflow");

    
//Creating toolboxItems
    ToolboxItemWrapper tool0 = new ToolboxItemWrapper(
        
"System.Activities.Statements.Assign",
        
"System.Activities, Version=4.0.0.0, Culture=neutral, PublicKeyToken=31bf3856ad364e35"
        ,
null,
        
"Assign");
    ToolboxItemWrapper tool1
= new ToolboxItemWrapper(
        
"System.Activities.Statements.Sequence",
        
"System.Activities, Version=4.0.0.0, Culture=neutral, PublicKeyToken=31bf3856ad364e35",
        
null,
        
"Sequence");
    ToolboxItemWrapper tool2
= new ToolboxItemWrapper(
        
"System.Activities.Statements.TryCatch",
        
"System.Activities, Version=4.0.0.0, Culture=neutral, PublicKeyToken=31bf3856ad364e35",
        
null,
        
"Try It"); // Can use a different name
    ToolboxItemWrapper tool3 = new ToolboxItemWrapper(
        
"HelloWorkflow.Activities.PrePostSequence",
        
"HelloWorkflow.Activities",
        
null,
        
"PrePostSequence");

    
//Adding the toolboxItems to the category.
    category.Add(tool0);
    category.Add(tool1);
    category.Add(tool2);
    category.Add(tool3);

    
//Adding the category to the ToolBox control.
    ctrl.Categories.Add(category);
    
return ctrl;
}

   (代码段- Introduction to WF4 Lab – CreateToolboxControl method VB)

Private Function CreateToolboxControl() As ToolboxControl
    
'Create the ToolBoxControl
    Dim ctrl As ToolboxControl = New ToolboxControl()

    
'Create a collection of category items
    Dim category As ToolboxCategory = New ToolboxCategory("Hello Workflow")

    
'Creating toolboxItems
    Dim tool0 As ToolboxItemWrapper = New ToolboxItemWrapper(
        
"System.Activities.Statements.Assign",
        
"System.Activities, Version=4.0.0.0, Culture=neutral, PublicKeyToken=31bf3856ad364e35",
        
Nothing,
        
"Assign")
    
Dim tool1 As ToolboxItemWrapper = New ToolboxItemWrapper(
        
"System.Activities.Statements.Sequence",
        
"System.Activities, Version=4.0.0.0, Culture=neutral, PublicKeyToken=31bf3856ad364e35",
        
Nothing,
        
"Sequence")
    
Dim tool2 As ToolboxItemWrapper = New ToolboxItemWrapper(
        
"System.Activities.Statements.TryCatch",
        
"System.Activities, Version=4.0.0.0, Culture=neutral, PublicKeyToken=31bf3856ad364e35",
        
Nothing,
        
"Try It") ' Can use a different name
    Dim tool3 As ToolboxItemWrapper = New ToolboxItemWrapper(
        
"HelloWorkflow.Activities.PrePostSequence",
        
"HelloWorkflow.Activities",
        
Nothing,
        
"PrePostSequence")

    
'Adding the toolboxItems to the category.
    category.Add(tool0)
    category.Add(tool1)
    category.Add(tool2)
    category.Add(tool3)

    
'Adding the category to the ToolBox control.
    ctrl.Categories.Add(category)
    
Return ctrl
End Function

 

  如下面所示,AddDesigner 函数把设计器加到你的窗口中。

  (代码段- Introduction to WF4 Lab – AddDesigner method CSharp)

private void AddDesigner()
{
    
//Create an instance of WorkflowDesigner class
    this.workflowDesigner = new WorkflowDesigner();

    
//Place the WorkflowDesigner in the middle column of the grid
    Grid.SetColumn(this.workflowDesigner.View, 1);

    
// Flush the workflow when the model changes
    workflowDesigner.ModelChanged += (s, e) =>
    {
        workflowDesigner.Flush();
        textXAML.Text
= workflowDesigner.Text;
    };

    
//Load a new Sequence as default.
    this.workflowDesigner.Load(new Sequence());

    
//Add the WorkflowDesigner to the grid
    grid1.Children.Add(this.workflowDesigner.View);

    
// Add the Property Inspector
    Grid.SetColumn(workflowDesigner.PropertyInspectorView, 2);
    grid1.Children.Add(workflowDesigner.PropertyInspectorView);

    
// Add the toolbox
    ToolboxControl tc = CreateToolboxControl();
    Grid.SetColumn(tc,
0);
    grid1.Children.Add(tc);
}

  (代码段- Introduction to WF4 Lab – AddDesigner method VB)

Private Sub AddDesigner()

    
'Create an instance of WorkflowDesigner class
    workflowDesigner = New WorkflowDesigner()

    
'Place the WorkflowDesigner in the middle column of the grid
    Grid.SetColumn(workflowDesigner.View, 1)

    
' Setup the Model Changed event handler
    AddHandler workflowDesigner.ModelChanged,
        
Function(sender As Object, e As System.EventArgs)
            
' Flush the workflow when the model changes
            workflowDesigner.Flush()
            textXAML.Text
= workflowDesigner.Text
            
Return Nothing
        
End Function

    
'Load a new Sequence as default.
    workflowDesigner.Load(New Sequence())

    
'Add the WorkflowDesigner to the grid
    grid1.Children.Add(workflowDesigner.View)

    
' Add the Property Inspector
    Grid.SetColumn(workflowDesigner.PropertyInspectorView, 2)
    grid1.Children.Add(workflowDesigner.PropertyInspectorView)

    
' Add the toolbox
    Dim tc As ToolboxControl = CreateToolboxControl()
    Grid.SetColumn(tc,
0)
    grid1.Children.Add(tc)
End Sub

   在构造函数中,以上的那些函数会被调用。

  (代码段- Introduction to WF4 Lab – MainWindow method CSharp)

public MainWindow()
{
    InitializeComponent();
    RegisterMetadata();
    AddDesigner();
}

  (代码段- Introduction to WF4 Lab – MainWindow method VB)

Public Sub New()
    
' This call is required by the designer.
    InitializeComponent()

    
' Add any initialization after the InitializeComponent() call.
    RegisterMetadata()
    AddDesigner()
End Sub
0
相关文章