推薦 百搜技術網:http://www.baisoujs.com html
基本介紹篇 android
本人推薦學習資料技術網:http://www.baisoujs.com/list_android_andarticle.html 瀏覽器
在實現這個擴展以前,讓咱們先弄清楚這個擴展實現什麼功能。這個擴展其實是在你的VS窗口的右上角建立了一個信息框代碼。該信息框顯示您的源代碼的統計信息。這些信息包括: 編輯器
一、文件的代碼行數 函數
二、文件的字符數 佈局
三、命名空間的個數 學習
四、字段個數 ui
五、接口個數 this
六、類的個數 spa
七、函數個數
八、屬性個數
九、註釋的數量
十、統計文件的大小(Bytes, KB, MB等)。
當您鍵入您的代碼,你會看到信息窗口中的數據會即時更新。
這個信息窗口,是利用可擴展面板。你能夠把它當作兩個部分,每個部分均可以根據您的須要展開和摺疊。這樣,當你不須要它時,你將它能夠摺疊起來,須要的時候,將它展開。下面演示如何展開/摺疊這個控件。
這個控件有三個特殊的狀態。第一個狀態是一個很小的擴展按鈕。如上圖的第一部分。只需點擊它,就會打開控件右側的面板,這個面板顯示文件的基本數據,如上圖的第二部分。這個控件還有一個可擴展面板,若是點擊擴展,就會看到下面的面板,其中顯示其餘的統計數據,如上圖的第三部分。
須要軟件:
一、 Microsoft Visual Studio 2010
二、 Visual Studio 2010 SDK
你安裝 Visual Studio SDK以後,你的Visual Studio 2010中會多出下面這些模板:
這篇文章中,咱們使用模板Editor ViewPort Adornment實現這個擴展,此模板將爲你的代碼編輯器的帶來一個裝飾品。
其實這個擴展包一個WPF用戶控件,我把它放進VS的視窗中就成了信息框。它還含有兩個類,一個類用來解析代碼,獲取代碼的相關信息;另外一個類用來處理自定義編輯器的事件和當頁以及加載的時候將WPF控件添加到頁面中。
咱們從Extensibility中選擇Viewport Adornment模板建立一個項目。這將生成一個SourceManifest文件和兩個類文件。一個是Adornment類自己,另一個是AdornmentFactory類。
右鍵單擊項目,選擇添加一個新的WPF用戶控件。爲了簡單起見,我使用了一個用戶控件。這個用戶控件實際上包含一個Expander控件,設置它的ExpandDirection = Left,它裏面又包含了一些TextBlock控件和另一個Expander ,設置裏面的這個Expander的ExpandDirection = Down。看下面的代碼(我刪除沒必要要的元素,使其更簡單):
你能夠看到,代碼很簡單,兩個Expanders,一個用來顯示基本的統計信息和另一個顯示擴展的統計信息。我還使用StackPanel來固定TextBlocks佈局。
如今,若是你看一下後臺代碼,發現它也同樣簡單。其實我已經建立了一個CodeInfoTracker類,用它來爲咱們分析源代碼文件。我只是爲咱們的用戶控件添加了一個構造函數,使用戶控件更具擴展性而已。
//百搜技術:http://www.baisoujs.com
private CodeInfoTracker _cinfo; private CodeInfoTracker.Calculators _calculator; public ucInfoBox(CodeInfoTracker cinfo) : this() { this._cinfo = cinfo; } public void UpdateInfo(CodeInfoTracker info) { _calculator = info.PerFormCalculate(); this.txtNoLines.Text = string.Format("No of Lines : {0}", _calculator.no_of_lines); this.txtNoCharacters.Text = string.Format("No of Characters : {0}", _calculator.no_of_characters); this.txtFileSize.Text = string.Format("Total File Size : {0}", _calculator.totalfilesize); StringBuilder builder = new StringBuilder(); if (this._calculator.interfaces != 0) builder.AppendFormat("Interfaces : {0}\n\r", this._calculator.interfaces); if (this._calculator.namespaces != 0) builder.AppendFormat("NameSpaces : {0}\n\r", this._calculator.namespaces); if (this._calculator.classes != 0) builder.AppendFormat("Classes : {0}\n\r", this._calculator.classes); if (this._calculator.methods != 0) builder.AppendFormat("Methods : {0}\n\r", this._calculator.methods); if (this._calculator.properties != 0) builder.AppendFormat("Properties : {0}\n\r", this._calculator.properties); if (this._calculator.fields != 0) builder.AppendFormat("Fields : {0}\n\r", this._calculator.fields); if (this._calculator.comments != 0) builder.AppendFormat("Comments : {0}\n\r", this._calculator.comments); if (builder.Length > 0) { this.txtClassInfo.Visibility = System.Windows.Visibility.Visible; this.txtClassInfo.Text = builder.ToString(); } else { this.txtClassInfo.Text = ""; this.txtClassInfo.Visibility = System.Windows.Visibility.Hidden; } }
使用了一個結構體Calculators ,這個結構體放置在咱們的自定義類中,它有幾個int屬性用來保存分析源文件獲取的全部信息。 info.PerFormCalculate(); 給出分析的結果。這裏使用的全部獲取的信息來更新了UIElements。
雖然代碼存在一些複雜性,可是這個類其實很簡單。我很感謝CS Parser ,它幫助我自動地解析源代碼。
這個類須要一個IWpfTextView對象,它表明着Visual Studio文本編輯器。實際上WpfTextView實現了IWpfTextView。在執行期間這個類接受這個對象。我能夠從WPFTextView.TextSnapshot.GetText()得到到了源代碼。
在我調用的這個分析的時候,我只須要檢測的代碼是什麼語言寫的。開始我想本身來實現,可是感謝上帝,我在WPFTextView中發現已經存在這個對象了。
//百搜技術:http://www.baisoujs.com
public enum Language { CSharp, VisualBasic, Indeterminate } internal Language DetectLanguage { get { string langtype = this._view.FormattedLineSource.TextAndAdornmentSequencer. SourceBuffer.ContentType.DisplayName; if(langtype.Equals("CSHARP", StringComparison.InvariantCultureIgnoreCase)) return Language.CSharp; else if(langtype.Equals("BASIC", StringComparison.InvariantCultureIgnoreCase)) return Language.VisualBasic; else return Language.Indeterminate; } }
DetectLanguage妥善地利用WPFTextView對象的FormattedLineSource.TextAndAdornmentSequencer.
SourceBuffer.ContentType.DisplayName,這個屬性告訴我是使用了哪一種語言。以後我建立了一個新的方法PerFormCalculate,用它來解析源代碼,它返回一個Calculation結構對象。
回到這個擴展,我建立一個Adornment(InfoBoxAdornmentFactory)的Factory類。這個類繼承IWpfTextViewCreationListener,用來監聽WPF的編輯和建立事件。
[Export(typeof(IWpfTextViewCreationListener))] [ContentType("text")] [TextViewRole(PredefinedTextViewRoles.Document)] internal sealed class InfoBoxAdornmentFactory : IWpfTextViewCreationListener { [Export(typeof(AdornmentLayerDefinition))] [Name("AlwaysVisibleInfoBox")] [Order(After = PredefinedAdornmentLayers.Selection)] [TextViewRole(PredefinedTextViewRoles.Interactive)] public AdornmentLayerDefinition editorAdornmentLayer = null; public void TextViewCreated(IWpfTextView textView) { new AlwaysVisibleInfoBox(textView); } }
這裏,你能夠看到我在這個類上使用了不少Attributes,像ContentType,它定義了咱們只處理文本格式的編輯器;還有TextViewRole,它定義了將被這個類處理的textview的類型。
在這個類中,我建立了一個AdornmentLayerDefination對象。可能你想知道咱們沒有使用它,無什麼還須要定義它呢,它只是用來配置屬性的。Order屬性指定,當,InfoBox在層被選以後監聽,Name是編輯擴展的名字。
Adornment類實際建立了一個WPF用戶控件對象,並設置它的視圖畫布。在內部構造函數中,我處理IWpfTextView.LayoutChanged事件,當代碼修改或者佈局改變的時候,就觸發這個事件。所以,經過這一事件,當咱們編輯的文檔時,咱們能夠很容易地獲得回調。當瀏覽器編輯器的大小改變時,我還經過處理WPFTextView.ViewportHeightChanged,WPFTextView.ViewportWidthChanged獲得回調,使咱們能夠從新定位相應的UserControl。
//百搜技術:http://www.baisoujs.com
public AlwaysVisibleInfoBox(IWpfTextView view) { _view.LayoutChanged += this.OnLayoutChanged; this.GetLayer(); }
//http://www.baisoujs.com private void GetLayer() { _adornmentLayer = this._view.GetAdornmentLayer("AlwaysVisibleInfoBox"); _view.ViewportHeightChanged += delegate { this.onSizeChange(); }; _view.ViewportWidthChanged += delegate { this.onSizeChange(); }; } private void OnLayoutChanged(object sender, TextViewLayoutChangedEventArgs e) { this._info = new CodeInfoTracker(_view); this.infobox.UpdateInfo(this._info); } public void onSizeChange() { _adornmentLayer.RemoveAllAdornments(); Canvas.SetLeft(infobox, _view.ViewportRight - 255); Canvas.SetTop(infobox, _view.ViewportTop + 10); _adornmentLayer.AddAdornment(AdornmentPositioningBehavior.ViewportRelative, null, null, infobox, null); }
所以,構造函數只是調用GetLayer來獲取的Layer對象,發生在ViewportHeightChanged和ViewportWidthChanged ViewPortSizeChage事件。當一個佈局改變時,我就能更新這個用戶的控件。
至此,咱們成功地創建咱們的擴展。你可使用F5運行它,它會打開一個Visual Studio的Experimental實例。
安裝和卸載這個擴展是很是容易的。當您編譯項目後,它會產生一個VSIX文件。您能夠只需雙擊這個文件,它會自動安裝到Visual Studio。
要卸載的文件,您打開Visual Studio,轉到 Tools - > Extension Manager,而後選擇卸載該擴展。
發佈你的擴展到Visual Studio庫的方式也很是的酷。只要你須要上傳VSIX文件到http://www.baisoujs.com/detail_137433956352461.html。我已經上載個人這個擴展。
//百搜技術:http://www.baisoujs.com