From 4c9a3527cb9d88fd8aef2dcf822a7a07ad3d89c6 Mon Sep 17 00:00:00 2001 From: Daniel Grunwald Date: Wed, 17 Mar 2010 21:14:02 +0000 Subject: [PATCH] Fixed bug that could cause the text editor's ParseInformation to get out-of-sync with the parser service's. Removed IParseInformationListener as it was unreliable (depended on view content), use ParserService.ParseInformationUpdated instead. git-svn-id: svn://svn.sharpdevelop.net/sharpdevelop/trunk@5623 1ccf3a8d-04fe-1044-b7c0-cef0b8235c61 --- .../Src/AvalonEditViewContent.cs | 23 +------------- .../AvalonEdit.AddIn/Src/CodeEditor.cs | 30 ++++++++++++++++--- .../Project/ICSharpCode.SharpDevelop.csproj | 1 - .../IParseInformationListener.cs | 17 ----------- .../ParseInformationEventArgs.cs | 15 +++++++--- .../Services/ParserService/ParserService.cs | 15 +++------- 6 files changed, 42 insertions(+), 59 deletions(-) delete mode 100644 src/Main/Base/Project/Src/Gui/ContentInterfaces/IParseInformationListener.cs diff --git a/src/AddIns/DisplayBindings/AvalonEdit.AddIn/Src/AvalonEditViewContent.cs b/src/AddIns/DisplayBindings/AvalonEdit.AddIn/Src/AvalonEditViewContent.cs index 7c971fc5b2..d55dae8960 100644 --- a/src/AddIns/DisplayBindings/AvalonEdit.AddIn/Src/AvalonEditViewContent.cs +++ b/src/AddIns/DisplayBindings/AvalonEdit.AddIn/Src/AvalonEditViewContent.cs @@ -27,7 +27,7 @@ namespace ICSharpCode.AvalonEdit.AddIn } public class AvalonEditViewContent - : AbstractViewContent, IEditable, IMementoCapable, ICodeEditorProvider, IPositionable, IParseInformationListener, IToolsHost + : AbstractViewContent, IEditable, IMementoCapable, ICodeEditorProvider, IPositionable, IToolsHost { readonly CodeEditor codeEditor = new CodeEditor(); @@ -261,27 +261,6 @@ namespace ICSharpCode.AvalonEdit.AddIn } #endregion - #region IParseInformationListener - ParseInformation updateParseInfoTo; - - public void ParseInformationUpdated(ParseInformation parseInfo) - { - WorkbenchSingleton.AssertMainThread(); - // When parse information is updated quickly in succession, only do a single update - // to the latest version. - updateParseInfoTo = parseInfo; - codeEditor.Dispatcher.BeginInvoke( - DispatcherPriority.Background, - new Action( - delegate { - if (updateParseInfoTo != null) { - codeEditor.ParseInformationUpdated(updateParseInfoTo); - updateParseInfoTo = null; - } - })); - } - #endregion - object IToolsHost.ToolsContent { get { return TextEditorSideBar.Instance; } } diff --git a/src/AddIns/DisplayBindings/AvalonEdit.AddIn/Src/CodeEditor.cs b/src/AddIns/DisplayBindings/AvalonEdit.AddIn/Src/CodeEditor.cs index 62eab02257..7034b5674f 100644 --- a/src/AddIns/DisplayBindings/AvalonEdit.AddIn/Src/CodeEditor.cs +++ b/src/AddIns/DisplayBindings/AvalonEdit.AddIn/Src/CodeEditor.cs @@ -137,6 +137,7 @@ namespace ICSharpCode.AvalonEdit.AddIn { CodeEditorOptions.Instance.PropertyChanged += CodeEditorOptions_Instance_PropertyChanged; CustomizedHighlightingColor.ActiveColorsChanged += CustomizedHighlightingColor_ActiveColorsChanged; + ParserService.ParseInformationUpdated += ParserServiceParseInformationUpdated; this.CommandBindings.Add(new CommandBinding(SharpDevelopRoutedCommands.SplitView, OnSplitView)); @@ -492,14 +493,34 @@ namespace ICSharpCode.AvalonEdit.AddIn { ParseInformation parseInfo = ParserService.GetExistingParseInformation(this.FileName); if (parseInfo == null) { - // if parse info is not yet available, start parsing - var future = ParserService.BeginParse(this.FileName, primaryTextEditorAdapter.Document); - if (future.Wait(50)) - parseInfo = future.Result; + // if parse info is not yet available, start parsing on background + ParserService.BeginParse(this.FileName, primaryTextEditorAdapter.Document); + // we'll receive the result using the ParseInformationUpdated event } ParseInformationUpdated(parseInfo); } + ParseInformation updateParseInfoTo; + + void ParserServiceParseInformationUpdated(object sender, ParseInformationEventArgs e) + { + if (e.FileName != this.FileName) + return; + this.VerifyAccess(); + // When parse information is updated quickly in succession, only do a single update + // to the latest version. + updateParseInfoTo = e.NewParseInformation; + this.Dispatcher.BeginInvoke( + DispatcherPriority.Background, + new Action( + delegate { + if (updateParseInfoTo != null) { + ParseInformationUpdated(updateParseInfoTo); + updateParseInfoTo = null; + } + })); + } + public void ParseInformationUpdated(ParseInformation parseInfo) { if (parseInfo != null && CodeEditorOptions.Instance.EnableQuickClassBrowser) { @@ -531,6 +552,7 @@ namespace ICSharpCode.AvalonEdit.AddIn { CodeEditorOptions.Instance.PropertyChanged -= CodeEditorOptions_Instance_PropertyChanged; CustomizedHighlightingColor.ActiveColorsChanged -= CustomizedHighlightingColor_ActiveColorsChanged; + ParserService.ParseInformationUpdated -= ParserServiceParseInformationUpdated; primaryTextEditorAdapter.Language.Detach(); if (secondaryTextEditorAdapter != null) diff --git a/src/Main/Base/Project/ICSharpCode.SharpDevelop.csproj b/src/Main/Base/Project/ICSharpCode.SharpDevelop.csproj index 40a19af3f9..857752fe76 100644 --- a/src/Main/Base/Project/ICSharpCode.SharpDevelop.csproj +++ b/src/Main/Base/Project/ICSharpCode.SharpDevelop.csproj @@ -416,7 +416,6 @@ Form - diff --git a/src/Main/Base/Project/Src/Gui/ContentInterfaces/IParseInformationListener.cs b/src/Main/Base/Project/Src/Gui/ContentInterfaces/IParseInformationListener.cs deleted file mode 100644 index ea6e01c144..0000000000 --- a/src/Main/Base/Project/Src/Gui/ContentInterfaces/IParseInformationListener.cs +++ /dev/null @@ -1,17 +0,0 @@ -// -// -// -// -// $Revision$ -// - -using System; -using ICSharpCode.SharpDevelop.Dom; - -namespace ICSharpCode.SharpDevelop.Gui -{ - public interface IParseInformationListener - { - void ParseInformationUpdated(ParseInformation parseInfo); - } -} diff --git a/src/Main/Base/Project/Src/Services/ParserService/ParseInformationEventArgs.cs b/src/Main/Base/Project/Src/Services/ParserService/ParseInformationEventArgs.cs index e61b0bbdac..e59dda2aee 100644 --- a/src/Main/Base/Project/Src/Services/ParserService/ParseInformationEventArgs.cs +++ b/src/Main/Base/Project/Src/Services/ParserService/ParseInformationEventArgs.cs @@ -16,7 +16,7 @@ namespace ICSharpCode.SharpDevelop FileName fileName; IProjectContent projectContent; ICompilationUnit oldCompilationUnit; - ICompilationUnit newCompilationUnit; + ParseInformation newParseInformation; public FileName FileName { get { return fileName; } @@ -33,14 +33,21 @@ namespace ICSharpCode.SharpDevelop get { return oldCompilationUnit; } } + /// + /// The new parse information. + /// + public ParseInformation NewParseInformation { + get { return newParseInformation; } + } + /// /// The new compilation unit. /// public ICompilationUnit NewCompilationUnit { - get { return newCompilationUnit; } + get { return newParseInformation.CompilationUnit; } } - public ParseInformationEventArgs(FileName fileName, IProjectContent projectContent, ICompilationUnit oldCompilationUnit, ICompilationUnit newCompilationUnit) + public ParseInformationEventArgs(FileName fileName, IProjectContent projectContent, ICompilationUnit oldCompilationUnit, ParseInformation newParseInformation) { if (fileName == null) throw new ArgumentNullException("fileName"); @@ -49,7 +56,7 @@ namespace ICSharpCode.SharpDevelop this.fileName = fileName; this.projectContent = projectContent; this.oldCompilationUnit = oldCompilationUnit; - this.newCompilationUnit = newCompilationUnit; + this.newParseInformation = newParseInformation; } } diff --git a/src/Main/Base/Project/Src/Services/ParserService/ParserService.cs b/src/Main/Base/Project/Src/Services/ParserService/ParserService.cs index b2d3e658ae..b85e3c231e 100644 --- a/src/Main/Base/Project/Src/Services/ParserService/ParserService.cs +++ b/src/Main/Base/Project/Src/Services/ParserService/ParserService.cs @@ -425,12 +425,15 @@ namespace ICSharpCode.SharpDevelop } } + ParseInformation newParseInfo = new ParseInformation(resultUnit); + for (int i = 0; i < newUnits.Length; i++) { IProjectContent pc = projectContents[i]; // update the compilation unit ICompilationUnit oldUnit = oldUnits.FirstOrDefault(o => o.ProjectContent == pc); pc.UpdateCompilationUnit(oldUnit, newUnits[i], fileName); - RaiseParseInformationUpdated(new ParseInformationEventArgs(fileName, pc, oldUnit, newUnits[i])); + ParseInformation newUnitParseInfo = (newUnits[i] == resultUnit) ? newParseInfo : new ParseInformation(newUnits[i]); + RaiseParseInformationUpdated(new ParseInformationEventArgs(fileName, pc, oldUnit, newUnitParseInfo)); } // remove all old units that don't exist anymore @@ -443,7 +446,6 @@ namespace ICSharpCode.SharpDevelop this.bufferVersion = fileContentVersion; this.oldUnits = newUnits; - ParseInformation newParseInfo = new ParseInformation(resultUnit); this.parseInfo = newParseInfo; TaskService.UpdateCommentTags(fileName, resultUnit.TagComments); return newParseInfo; @@ -758,15 +760,6 @@ namespace ICSharpCode.SharpDevelop WorkbenchSingleton.SafeThreadAsyncCall( delegate { ParseInformationUpdated(null, e); - - IViewContent currentView = WorkbenchSingleton.Workbench.ActiveViewContent; - IParseInformationListener listener = currentView as IParseInformationListener; - if (listener != null && FileUtility.IsEqualFileName(e.FileName, currentView.PrimaryFileName)) { - if (e.NewCompilationUnit != null) - listener.ParseInformationUpdated(new ParseInformation(e.NewCompilationUnit)); - else - listener.ParseInformationUpdated(null); - } }); }