/// <summary> /// Registers for code model events. /// </summary> private void AdviseCodeModelEvents() { try { languageService.OnFileCodeModelChanged += OnFileCodeModelChanged; var dte2 = dte as DTE2; if (dte2 == null) { throw new NullReferenceException("dte2 is NULL"); } var events2 = dte2.Events as Events2; if (events2 == null) { throw new NullReferenceException("events2 is NULL"); } codeModelEvents = events2.get_CodeModelEvents(null); if (codeModelEvents != null) { codeModelEvents.ElementAdded += codeModelEvents_Added; codeModelEvents.ElementChanged += codeModelEvents_Changed; codeModelEvents.ElementDeleted += codeModelEvents_Deleted; } } catch (ArgumentException) { // Failed to get CodeModelEvents, this should not occur. SourceOutlineToolWindow.DisplayMessage(Resources.ErrorPrefix, "Failed to get Code Model events."); throw; } }
/// <summary> /// Loads a document into display TreeViews, updates the cache, and /// rebuilds the file manager that represents the document. /// </summary> /// <param name="d">The Document to load.</param> /// <param name="tw">The tool window associated with the cache.</param> /// <remarks> /// If the document is in the cache, it is reused. /// </remarks> public void AddDocumentToCache(Document d, SourceOutlineToolWindow tw) { Debug.Assert(d != null); _toolWindow = tw; if (d == _document) { return; } if (_document != null) { // Unregister events for the previous document. tw.UnRegisterTreeEvents(fileManager.TreeView, fileManager.FilterView); control.RemoveTreeFromControls(fileManager.TreeView); control.RemoveTreeFromControls(fileManager.FilterView); } _document = d; fileManager = new CodeOutlineFileManager(control, dte, d, tw, languageService); tw.RegisterTreeEvents(fileManager.TreeView, fileManager.FilterView); // Load the control. control.AddTreeToControls(fileManager.TreeView); control.AddTreeToControls(fileManager.FilterView); fileManager.State = CodeOutlineFileManager.OutlineFileManagerState.StartLoadingCodeModel; fileManager.HideTrees(); control.HideTrees(); control.TreeView = fileManager.TreeView; control.FilterView = fileManager.FilterView; // Re-display the last CodeElementType selected for this document. tw.SelectedType = fileManager.ElementFilter; // Re-display the last filter text entered for this document, but only if the file is loaded. if (fileManager.State == CodeOutlineFileManager.OutlineFileManagerState.DoneLoadingCodeModel) { fileManager.ReApplyText(); tw.SelectedFilterText = fileManager.FilterText; } else { control.Reset(); } }
/// <summary> /// Raised when a CodeElement object has been changed. /// </summary> /// <param name="modifiedElement">The CodeElement that was changed.</param> /// <param name="iChangeType">The type of change event that was fired.</param> private void codeModelEvents_Changed(CodeElement modifiedElement, vsCMChangeKind iChangeType) { try { if (CurrentFileManager == null) { return; } ForceReload(); } catch (Exception ex) { SourceOutlineToolWindow.DisplayMessage(Resources.ErrorPrefix, "codeModelEvents_Changed exception: " + ex); } }
/// <summary> /// Raised when a FileCodeModel object has been changed. /// </summary> /// <param name="sender"></param> /// <param name="e"></param> private void OnFileCodeModelChanged(object sender, FileCodeModelChangedEventArgs e) { try { if (CurrentFileManager == null) { return; } SourceOutlineToolWindow.DisplayMessage(Resources.StatusPrefix, "OnFileCodeModelChanged fired."); control.Invoke(new MethodInvoker(ForceReload)); } catch (Exception ex) { SourceOutlineToolWindow.DisplayMessage(Resources.ErrorPrefix, "OnFileCodeModelChanged exception: " + ex); } }
/// <summary> /// Raised when a CodeElement object has been deleted. /// </summary> /// <param name="parent">The parent object for the CodeElement.</param> /// <param name="deletedElement">The CodeElement object that was deleted.</param> private void codeModelEvents_Deleted(object parent, CodeElement deletedElement) { try { if (CurrentFileManager == null) { return; } if (!CurrentFileManager.FileIsOutlined) { ForceReload(); return; } fileManager.OnCodeModelElementDeleted(parent, deletedElement); } catch (Exception ex) { SourceOutlineToolWindow.DisplayMessage(Resources.ErrorPrefix, "codeModelEvents_Deleted exception: " + ex); } }
/// <summary> /// Raised when a CodeElement object has been created. /// </summary> /// <param name="newElement">The CodeElement object that was added.</param> private void codeModelEvents_Added(CodeElement newElement) { try { if (CurrentFileManager == null) { return; } if (!CurrentFileManager.FileIsOutlined) { ForceReload(); return; } control.ShowWaitWhileReadyMessage(); fileManager.OnCodeModelElementAdd(newElement); control.HideWaitWhileReadyMessage(); } catch (Exception ex) { SourceOutlineToolWindow.DisplayMessage(Resources.ErrorPrefix, "codeModelEvents_Added exception: " + ex); } }
/// <summary> /// Initializes the DTE and the code outline file manager, and hooks up events. /// </summary> private void InitializeSourceOutlinerToolWindow() { var dte = GetService(typeof(_DTE)) as DTE; sourceOutlinerWindow = (SourceOutlineToolWindow)FindToolWindow(typeof(SourceOutlineToolWindow), 0, true); sourceOutlinerWindow.Package = this; OLECRINFO[] crinfo = new OLECRINFO[1]; crinfo[0].cbSize = (uint)Marshal.SizeOf(typeof(OLECRINFO)); crinfo[0].grfcrf = (uint)_OLECRF.olecrfNeedIdleTime | (uint)_OLECRF.olecrfNeedPeriodicIdleTime | (uint)_OLECRF.olecrfNeedAllActiveNotifs | (uint)_OLECRF.olecrfNeedSpecActiveNotifs; crinfo[0].grfcadvf = (uint)_OLECADVF.olecadvfModal | (uint)_OLECADVF.olecadvfRedrawOff | (uint)_OLECADVF.olecadvfWarningsOff; crinfo[0].uIdleTimeInterval = 500; int hr = componentManager.FRegisterComponent(sourceOutlinerWindow, crinfo, out componentID); if (!ErrorHandler.Succeeded(hr)) { Trace.WriteLine("Initialize->IOleComponent registration failed"); } sourceOutlinerWindow.InitializeDTE(dte); sourceOutlinerWindow.AddWindowEvents(); sourceOutlinerWindow.AddSolutionEvents(); }
/// <summary> /// Initializes a new instance of the CodeOutlineFileManager class. /// </summary> /// <param name="control">The outline control object.</param> /// <param name="dte">A DTE object exposing the Visual Studio automation object model.</param> /// <param name="d">The source file Document.</param> /// <param name="toolWindow">The tool window for the package.</param> /// <param name="languageService">The Lua LanguageService.</param> public CodeOutlineFileManager(SourceOutlinerControl control, DTE dte, Document d, SourceOutlineToolWindow toolWindow, LanguageService languageService) { this.languageService = languageService; this.control = control; this.dte = dte; sourceOutlineToolWindow = toolWindow; viewType = ViewType.TreeView; searchCriteria = new SearchCriteria(CodeElementType.All); currentFilterText = ""; currentDocument = d; codeTreeView = new TreeView(); codeFilterView = new TreeView(); // // codeTreeView // codeTreeView.Dock = DockStyle.Fill; codeTreeView.HideSelection = false; codeTreeView.Location = new Point(0, 45); codeTreeView.Name = "codeTreeView"; codeTreeView.ShowNodeToolTips = true; codeTreeView.Size = new Size(352, 294); codeTreeView.TabIndex = 2; // // codeFilterView // codeFilterView.Dock = DockStyle.Fill; codeFilterView.HideSelection = false; codeFilterView.Location = new Point(0, 45); codeFilterView.Name = "codeFilterView"; codeFilterView.ShowNodeToolTips = true; codeFilterView.Size = new Size(352, 294); codeFilterView.TabIndex = 3; codeFilterView.Visible = false; codeFilterView.ShowLines = false; codeFilterView.ShowRootLines = false; codeFilterView.FullRowSelect = true; }