2011-02-26 92 views

回答

37

使用自定义的外部工具有一个简单的方法(尽管不是所有满意的)。

假设你的项目文件的以下修改:

<Target Name="CalledFromIde"> 
    <Error Text="Called from the IDE!" /> 
    </Target> 

转到工具|外部工具,并添加一个这样的:

Title:  Called from IDE 
    Command: C:\Windows\Microsoft.NET\Framework64\v4.0.30319\MSBuild.exe 
    Arguments: $(ProjectDir)$(ProjectFileName) /t:CalledFromIde 
    Initial directory: $(ProjectDir) 
    Use Output window: checked 

运行此产生输出为:

Build FAILED. 

    "F:\Code\CsProject\CsProject.csproj" (CalledFromIde target) (1) -> 
    (CalledFromIde target) -> 
    F:\Code\CsProject\CsProject.csproj(57,5): error : Called from the IDE! 

你在做什么在呼唤出来的MSBuild作为外部工具,并让它直接运行的目标。您必须提供MSBuild的完整路径,因为IDE不会保留与其创建的构建环境相同的属性。

您可以通过计算出它在Tools.ExternalCommand#集合中的哪个命令#来将它连接到快捷方式。

如果您正在寻找一个更复杂的解决方案,它会涉及更多一点。这里简单地说(VS2010):

1)创建一个VS Addin(File | New | Project | Other Project Types | Extensibility | Visual Studio Add-in)。我不确定您是否必须安装VS SDK才能获得该版本,它可以在扩展管理器中找到。

在向导中选择下列选项: - 微软的Visual Studio 2010 - 是的,创建“工具”菜单项 - 加载应用程序启动时 - 我的外接绝不会容忍模式UI,和可以与命令行构建一起使用。

2)添加引用Microsoft.Build和Microsoft.Build.Framework

3)查找Exec的在Connect.cs实现文件

4)替换为以下代码:

public void Exec(
    string commandName, 
    vsCommandExecOption executeOption, 
    ref object varIn, 
    ref object varOut, 
    ref bool handled) 
{ 
    handled = false; 
    if (executeOption != vsCommandExecOption.vsCommandExecOptionDoDefault) 
     return; 
    if (commandName != "BuildAddin.Connect.BuildAddin") 
     return; 

    var doc = _applicationObject.ActiveDocument; 
    var projectItem = doc.ProjectItem; 
    var project = projectItem.ContainingProject; 
    var evalProject = 
     Microsoft.Build.Evaluation.ProjectCollection 
     .GlobalProjectCollection.LoadProject(project.FullName); 
    var execProject = evalProject.CreateProjectInstance(); 

    bool success = execProject.Build("CalledFromIde", null); 

    var window = _applicationObject.Windows.Item(Constants.vsWindowKindOutput); 
    var output = (OutputWindow)window.Object; 
    OutputWindowPane pane = output.OutputWindowPanes.Add("BuildAddin"); 
    pane.OutputString(success ? "built /t:CalledFromIde" : "build failed"); 

    handled = true; 
    return; 
} 

5)在调试好自定义的目标,因为以前的一个错误:

<Target Name="CalledFromIde"> 
    <WriteLinesToFile File="CalledFromIde.txt" Lines="Called from the IDE!" /> 
    </Target> 

6)为简洁起见,上面的代码没有错误检查,因为它将在IDE中运行,所以您希望更清洁。插件会在你的工具菜单上放置一个菜单项。如上所述,它只是寻找包含当前活动编辑器文档的项目,无论你做什么,都需要更好的管道。

该技巧从IDE中获取构建引擎实例,并使其在单独的项目实例上执行构建。

2

你不必用Exec编写代码,尽管这是一种方法。更简单的方法是做到以下几点:

更改DefaultTargets="Build"属性自定义目标创建,说"All"像这样:

DefaultTargets="All" 

然后在您的自定义的“所有”目标,您可以使用DependsOnTargets属性,如下所示:

"<Target Name="All" DependsOnTargets="ZipOutputFiles;Build"> 
    </Target>" 

然后,这将建立和出把zip文件在您的自定义"All"目标。

3

如果您在Visual Studio中运行构建,则在构建期间将会有VisualStudioDir的构建变量。

仅执行是VS建立会话做到这一点:

<Target Name="Test" BeforeTargets="Build" Condition="'$(VisualStudioDir)' != ''> 
</Target> 

要只在VS之外构建执行此操作:

<Target Name="Test" BeforeTargets="Build" Condition="'$(VisualStudioDir)' == ''> 
</Target> 

您将需要包括您的自定义目标文件以两种方式之一。

  1. 设置环境变量CustomBeforeMicrosoftCommonTargets
  2. 编辑你的项目文件中加入进口

    <Imports Project="CustomBuildTasks.Targets"><Imports/> 
    
,包括您的自定义目标文件