2010-09-07 65 views
1

我創建了一個自定義VS模板,它使用IWizard類在用戶創建項目以設置項目屬性和路徑時執行一些自動操作,我設法設置一些項目屬性,如構建路徑,方法是在RunStarted方法期間,使用$ signs內的參數保存.csproj文件,並在replacementDictionary中設置這些參數。在創建項目期間添加一個鏈接到現有項目

不幸的是,我無法添加項目作爲鏈接到.csproj使用相同的方法。我需要添加一個.cs文件作爲已創建的每個項目的現有項目和鏈接項目,它的路徑將由用戶選擇保存項目的位置決定。我已經到了知道.cs文件路徑的部分(絕對的和相對於項目的路徑)。

這裏是我試過到目前爲止:

  • 保存的.csproj文件,該項目的一部分,與佔位符的路徑:
    <Compile Include="$path_to_cs_file\cs_file_name.cs$">
    <Link>$cs_file_name.cs$</Link>
    </Compile>

我試着用絕對路徑和相對路徑來做這件事,但是這個出於某種原因使VS替換了完全不同的路徑Documents and Settings \ user \ Local Settings下的相對路徑。

  • 在RunStarted中,將automationObject轉換爲DTE並調用它的ItemOperations.AddExistingItem方法。使用任一路徑都會導致錯誤(參數不正確)。

  • 在ProjectFinishedGenerating中,保存項目的路徑,然後在RunFinished中,用該路徑創建一個Microsoft.Build.BuildEngine.Project對象,調用DTE命令保存所有文件並卸載項目,然後調用項目對象的AddNewItem方法和SetMetaData對得到的項目項,後來我保存項目,並與DTE對象重新加載它,這又導致同樣的錯誤作爲前

我想感謝所有幫助與主題,我敢很難過。先謝謝你。

回答

1

我設法「解決」這個問題,我所做的是以下幾點:

  • 不停的佔位符的的csproj,但從來沒有加入相關參數來替換詞典:

    <Compile Include="$path_to_cs_file$\$cs_file_name.cs$">
    <Link>$cs_file_name.cs$</Link>
    </Compile>

  • 在ProjectFinishedGenerated方法中,卸載項目,編輯csproj文件以替換路徑並重新加載項目:

    projectFileName = project.FullName
    // Unload file and manually add the linked item
    dte.ExecuteCommand("File.SaveAll");
    dte.ExecuteCommand("Project.UnloadProject"); // See Note Below
    StreamReader reader = new StreamReader(projectFileName);
    string content = reader.ReadToEnd();
    reader.Close();
    content = Regex.Replace(content, @"\$path_to_cs_file\$", ...);
    content = Regex.Replace(content, @"\$cs_file_name\$", ...);
    StreamWriter writer = new StreamWriter(projectFileName);
    writer.Write(content);
    writer.Close(); dte.ExecuteCommand("Project.ReloadProject");

注意:上面的代碼假定該項目需要修改當前選擇項目的時候,通常ProjectFinishedGenerating運行是這種情況,但是在多項目模板,或者如果你已經添加了一個手動投影到解決方案可能不是這種情況,您必須調用dte方法在項目瀏覽器中選擇您的「主」項目,然後繼續卸載,編輯和重新加載。該代碼這樣做會是這個樣子:
UIHierarchy UIH = dte2.ToolWindows.SolutionExplorer;
UIHierarchyItem UIHItem = UIH.UIHierarchyItems.Item(1);
UIHItem.UIHierarchyItems.Item(testProjectName).Select(vsUISelectionType.vsUISelectionTypeSelect);

0

我有完全相同的問題,它讓我生氣。

我已經找到了一個真正的解決辦法髒然而:

在我的情況,我使用的方法RunStarted如下:

EnvDTE.DTE dte = automationObject as EnvDTE.DTE; 
string solutionPath = System.IO.Path.GetDirectory(dte.DTE.Solution.FullName); 

這將返回包含文件夾「文件」的路徑。調用System.IO.Directory.Exists()確認這是一個有效的目錄,但是在檢查我的文件系統時,似乎這不存在。如果您將「文檔」替換爲「我的文檔」,然後繼續爲鏈接項目使用該路徑,則所有工作都完美無缺。

因此,VS似乎與「文檔」目錄別名混淆,因此默認爲一些瘋狂的「AppData」目錄。

我希望這可以幫助,但如果你找到一個更好的方式來做到這一點,請讓我知道!

+0

我還是設法找到一種解決方法,請參閱我的方法的答案,看看它是否適合你... – JohnoBoy 2010-09-19 06:29:34

+0

感謝您的解決方法,行之有效。唯一的問題似乎是運行後,我得到一個對話框,說「項目不可用」。我只需要點擊「確定」,一切都很好(該項目是可用的,並按預期工作)。你知道如何防止這個錯誤出現嗎?它發生在你身上嗎? – user450354 2010-09-20 08:59:14

+0

我忘了添加下面的命令:'dte.ExecuteCommand(「Project.ReloadProject」);',我認爲這會解決你的問題 – JohnoBoy 2010-09-21 09:36:44

0

,如果你不想更動IWizard另一種解決方案是設置CreateInPlace爲true在TemplateData您vstemplate。

<CreateInPlace>true</CreateInPlace>