您的位置:首页 > 其它

VS2013文件同步插件开发

2014-11-17 21:27 239 查看

一、插件功能描述

插件监控一个xml文件,当该文档有添加新元素在保存的时候将新增的元素同步到指定的目录下。

二、模板的选择

由于该功能是跟代码编辑有关的,要监控文档的保存事件,所以要在文档打开的时候就注册保存事件的响应方法。VS提供了一个接口,监听文档的打开事件,这个接口就是:IWpfTextViewCreationListener,接口代码如下,该接口只有一个方法,在文档打开的时候会调用TextViewCreated方法执行。

// 摘要:
//     Listens to text view created events.
public interface IWpfTextViewCreationListener
{
  // 摘要:
  //     Called when a text view having matching roles is created over a text data
  //     model having a matching content type.
  //
  // 参数:
  //   textView:
  //     The newly created text view.
  void TextViewCreated(IWpfTextView textView);
}


所以随便选择一个模板都是可以的,只要在项目里面将模板创建的插件入口类改为继承IWpfTextViewCreationListener接口,并实现其接口即可。由于该功能需要用到选项配置功能,所以我建议读者使用Visual Stuido Package模板,因为使用该模板添加选项页会比较容易。这是msdn上在使用Visual Studio Package模板的情况下如何添加选项页的教程:http://msdn.microsoft.com/en-us/library/bb166195.aspx。我选择的是Editor Text Adornment模板,因为该模板创建的入口类就是继承IWpfTextViewCreationListener接口,但是使用该模板的话,添加选项页会比较麻烦一点。

三、添加选项页

按照msdn上的教程,我们知道需要添加两个类:继承Package的类和继承DialogPage的类,过程我就不再赘述。如果紧紧按照msdn上的教程,你会发现在工具-选项下根本没有我们添加的选项页(非Visual Studio Package模板的情况),这是为什么呢?原来在我们的csproj文件和source.extension.vsixmanifest里缺少了一些元素,按照下面的步骤就可以实现添加选项页的功能:

1、打开source.extension.vsixmanifest,选择Assets选项,点击New按钮,弹出图-1窗口

namespace AppSettingsSync
{
public class TextViewListener
{
/// <summary>
/// 文档信息
/// </summary>
private ITextView _view;

private DTE _dte;
private Events _events;
private DocumentEvents _docEvents;
/// <summary>
/// 文档是否修改过
/// </summary>
private bool _isChanged;
/// <summary>
/// 保存的时候是否自动同步到其他AppSettings.xml
/// </summary>
private bool _isAutoReplace = true;
/// <summary>
/// 触发同步操作的AppSetting.xml
/// </summary>
private string _sourceFile;
/// <summary>
/// 要被同步的AppSettings.xml所在的文件目录
/// </summary>
private string _targetFolder;

/// <summary>
/// 打开文档时触发
/// </summary>
/// <param name="textView"></param>
public TextViewListener(IWpfTextView textView)
{
this._view = textView;
this._dte = ServiceProvider.GlobalProvider.GetService(typeof(DTE)) as DTE;
Properties props = this._dte.get_Properties("IStrong", "AppSettingsSync");
if (props == null)
return;
this._sourceFile = (string)props.Item("SourceXmlFilePath").Value;
//File.AppendAllText(@"D:\log.txt", "源文件" + this._sourceFile + "当前文件" + this._dte.ActiveDocument.FullName);
if (!this._dte.ActiveDocument.FullName.Equals(this._sourceFile, StringComparison.OrdinalIgnoreCase))
return;
//获取DTE对象
this._events = this._dte.Events;
this._docEvents = this._events.DocumentEvents;
//订阅文档保存和修改事件
this._docEvents.DocumentSaved += _docEvents_DocumentSaved;
this._view.TextBuffer.Changed += TextBuffer_Changed;
}

/// <summary>
/// 文档修改事件
/// </summary>
/// <param name="sender"></param>
/// <param name="e"></param>
void TextBuffer_Changed(object sender, Microsoft.VisualStudio.Text.TextContentChangedEventArgs e)
{
if (e.Changes.Count() > 0)
this._isChanged = true;
}

/// <summary>
/// 文档保存事件
/// </summary>
/// <param name="Document"></param>
async void _docEvents_DocumentSaved(Document Document)
{
try
{
//File.AppendAllText(@"D:\log.txt", "触发保存事件");
//获取Tool->Opetions->IStrong->AppSettingsSync配置项内容
Properties props = this._dte.get_Properties("IStrong", "AppSettingsSync");
if (props == null)
return;
this._sourceFile = (string)props.Item("SourceXmlFilePath").Value;
//保存时要同时满足是源AppSettings.xml文件和该文件有被修改过
if (Document.FullName.Equals(this._sourceFile, StringComparison.OrdinalIgnoreCase) && this._isChanged)
{
this._isAutoReplace = (bool)props.Item("IsAutoSync").Value;
this._targetFolder = (string)props.Item("TargetFolder").Value;
//手动选择要同步的文件
if (!this._isAutoReplace)
{
SelectFiles sf = new SelectFiles(this._sourceFile, this._targetFolder);
sf.ShowDialog();
this._isChanged = false;
}
else
{
//自动同步文件
string fileName = System.IO.Path.GetFileName(this._sourceFile);
string[] files = Directory.GetFiles(this._targetFolder, fileName, SearchOption.AllDirectories);
this._isChanged = false;
await SyncHelper.SyncAppSettings(this._sourceFile, files);
//同步完成后修改Visual Studio状态栏信息
IVsStatusbar bar = ServiceProvider.GlobalProvider.GetService(typeof(SVsStatusbar)) as IVsStatusbar;
bar.SetText("AppSettings配置文件同步完成。");
}
}
}
catch (Exception ex)
{
MessageBox.Show(ex.Message, "提示", MessageBoxButton.OK, MessageBoxImage.Error);
}
}
}
}


View Code
获取VS的主题颜色

/// <summary>
/// 将模态窗口的颜色设置为Visual Studio的背景色
/// </summary>
/// <param name="themeColor"></param>
/// <returns></returns>
private Color converVsThemeColor(vsThemeColors themeColor)
{
  DTE2 dte2 = (EnvDTE80.DTE2)System.Runtime.InteropServices.Marshal.
  GetActiveObject("VisualStudio.DTE.12.0");
  uint color = dte2.GetThemeColor(themeColor);
  int a = (int)color / 0x1000000;
  int b = (int)(color - a * 0x1000000) / 0x10000;
  int g = (int)(color - a * 0x1000000 - b * 0x10000) / 0x100;
  int r = (int)(color - a * 0x1000000 - b * 0x10000 - g * 0x100);
  return Color.FromArgb(0xFF, r, g, b);
}
内容来自用户分享和网络整理,不保证内容的准确性,如有侵权内容,可联系管理员处理 点击这里给我发消息
标签: 
相关文章推荐