diff --git a/src/AddIns/BackendBindings/Python/PythonBinding/Project/Src/PythonMemberResolver.cs b/src/AddIns/BackendBindings/Python/PythonBinding/Project/Src/PythonMemberResolver.cs index ef62a48825..12ff2667b3 100644 --- a/src/AddIns/BackendBindings/Python/PythonBinding/Project/Src/PythonMemberResolver.cs +++ b/src/AddIns/BackendBindings/Python/PythonBinding/Project/Src/PythonMemberResolver.cs @@ -119,8 +119,12 @@ namespace ICSharpCode.PythonBinding IMember FindMemberInParent(IMember parentMember, string memberName) { - IClass parentMemberClass = parentMember.ReturnType.GetUnderlyingClass(); - return FindMemberInClass(parentMemberClass, memberName); + IReturnType returnType = parentMember.ReturnType; + if (returnType != null) { + IClass parentMemberClass = returnType.GetUnderlyingClass(); + return FindMemberInClass(parentMemberClass, memberName); + } + return null; } } } diff --git a/src/AddIns/BackendBindings/Python/PythonBinding/Test/PythonBinding.Tests.csproj b/src/AddIns/BackendBindings/Python/PythonBinding/Test/PythonBinding.Tests.csproj index cfbaac957e..4a51b1f5f5 100644 --- a/src/AddIns/BackendBindings/Python/PythonBinding/Test/PythonBinding.Tests.csproj +++ b/src/AddIns/BackendBindings/Python/PythonBinding/Test/PythonBinding.Tests.csproj @@ -369,11 +369,13 @@ + + diff --git a/src/AddIns/BackendBindings/Python/PythonBinding/Test/Resolver/ResolveMemberWhenFieldHasNoReturnTypeTests.cs b/src/AddIns/BackendBindings/Python/PythonBinding/Test/Resolver/ResolveMemberWhenFieldHasNoReturnTypeTests.cs new file mode 100644 index 0000000000..4d5e778069 --- /dev/null +++ b/src/AddIns/BackendBindings/Python/PythonBinding/Test/Resolver/ResolveMemberWhenFieldHasNoReturnTypeTests.cs @@ -0,0 +1,40 @@ +// Copyright (c) AlphaSierraPapa for the SharpDevelop Team (for details please see \doc\copyright.txt) +// This code is distributed under the GNU LGPL (for details please see \doc\license.txt) + +using System; +using System.Collections; +using System.Collections.Generic; + +using ICSharpCode.PythonBinding; +using ICSharpCode.Scripting.Tests.Utils; +using ICSharpCode.SharpDevelop.Dom; +using ICSharpCode.SharpDevelop.Dom.CSharp; +using NUnit.Framework; +using PythonBinding.Tests.Utils; +using UnitTestingUtils = UnitTesting.Tests.Utils; + +namespace PythonBinding.Tests.Resolver +{ + [TestFixture] + public class ResolveMemberWhenFieldHasNoReturnTypeTests + { + [Test] + public void Resolve_FieldHasNoReturnType_DoesNotThrowNullReferenceException() + { + MockProjectContent projectContent = new MockProjectContent(); + UnitTestingUtils.MockClass c = new UnitTestingUtils.MockClass(projectContent, "Test"); + projectContent.SetClassToReturnFromGetClass("self", c); + DefaultField field = c.AddField("randomNumber"); + field.ReturnType = null; + ParseInformation parseInfo = new ParseInformation(c.CompilationUnit); + + ExpressionResult expression = new ExpressionResult("self.randomNumber.randint", ExpressionContext.Default); + PythonClassResolver classResolver = new PythonClassResolver(); + PythonLocalVariableResolver localVariableResolver = new PythonLocalVariableResolver(classResolver); + PythonMemberResolver resolver = new PythonMemberResolver(classResolver, localVariableResolver); + + PythonResolverContext context = new PythonResolverContext(parseInfo, expression, "class Test:\r\npass"); + Assert.DoesNotThrow(delegate { resolver.Resolve(context); }); + } + } +} diff --git a/src/AddIns/BackendBindings/Python/PythonBinding/Test/Resolver/ResolveRandomRandintTests.cs b/src/AddIns/BackendBindings/Python/PythonBinding/Test/Resolver/ResolveRandomRandintTests.cs new file mode 100644 index 0000000000..d471a876e7 --- /dev/null +++ b/src/AddIns/BackendBindings/Python/PythonBinding/Test/Resolver/ResolveRandomRandintTests.cs @@ -0,0 +1,38 @@ +// Copyright (c) AlphaSierraPapa for the SharpDevelop Team (for details please see \doc\copyright.txt) +// This code is distributed under the GNU LGPL (for details please see \doc\license.txt) + +using System; +using ICSharpCode.PythonBinding; +using ICSharpCode.SharpDevelop.Dom; +using NUnit.Framework; +using PythonBinding.Tests.Utils; + +namespace PythonBinding.Tests.Resolver +{ + [TestFixture] + public class ResolveRandomRandintTests : ResolveTestsBase + { + protected override ExpressionResult GetExpressionResult() + { + return new ExpressionResult("self.randomNumber.randint", ExpressionContext.Default); + } + + protected override string GetPythonScript() + { + return + "import random\r\n" + + "\r\n" + + "class Test:\r\n" + + " def __init__(self):\r\n" + + " self.randomNumber = random.random()\r\n" + + " self.randomNumber.randint\r\n" + + "\r\n"; + } + + [Test] + public void Resolve_RandomModuleCannotBeFound_NoNullRefererenceExceptionThrown() + { + Assert.IsNotNull(resolveResult as PythonMethodGroupResolveResult); + } + } +} diff --git a/src/AddIns/BackendBindings/XamlBinding/XamlBinding/XamlCodeCompletionBinding.cs b/src/AddIns/BackendBindings/XamlBinding/XamlBinding/XamlCodeCompletionBinding.cs index a0223bc88f..02855f0047 100644 --- a/src/AddIns/BackendBindings/XamlBinding/XamlBinding/XamlCodeCompletionBinding.cs +++ b/src/AddIns/BackendBindings/XamlBinding/XamlBinding/XamlCodeCompletionBinding.cs @@ -220,9 +220,9 @@ namespace ICSharpCode.XamlBinding start = ""; completionList.PreselectionLength = start.Length; } else if (mrr.ResolvedType.FullyQualifiedName == "System.Windows.Media.FontFamily") { - string text = context.ValueStartOffset > -1 ? context.RawAttributeValue.Substring(0, Math.Min(context.ValueStartOffset + 1, context.RawAttributeValue.Length)) : ""; + string text = context.ValueStartOffset > -1 ? context.RawAttributeValue.Substring(0, Math.Min(context.ValueStartOffset, context.RawAttributeValue.Length)) : ""; int lastComma = text.LastIndexOf(','); - completionList.PreselectionLength = lastComma == -1 ? context.ValueStartOffset + 1 : context.ValueStartOffset - lastComma; + completionList.PreselectionLength = lastComma == -1 ? context.ValueStartOffset : context.ValueStartOffset - lastComma - 1; } } } diff --git a/src/AddIns/BackendBindings/XamlBinding/XamlBinding/XamlParser.cs b/src/AddIns/BackendBindings/XamlBinding/XamlBinding/XamlParser.cs index c03df01f4b..1423a1e7aa 100644 --- a/src/AddIns/BackendBindings/XamlBinding/XamlBinding/XamlParser.cs +++ b/src/AddIns/BackendBindings/XamlBinding/XamlBinding/XamlParser.cs @@ -91,8 +91,8 @@ namespace ICSharpCode.XamlBinding public ICompilationUnit Parse(IProjectContent projectContent, string fileName, ITextBuffer fileContent) { - //using (new DebugTimerObject("background parser")) { - // Core.LoggingService.Info("file: " + fileName); + ICompilationUnit compilationUnit; + using (ParseAndLock(fileContent)) { var document = parser.LastDocument; @@ -101,9 +101,26 @@ namespace ICSharpCode.XamlBinding document.AcceptVisitor(visitor); - return visitor.CompilationUnit; + compilationUnit = visitor.CompilationUnit; } - //} + + // During project load all XAML files are parsed + // most of them are not opened, thus fileContent.Version is null. + // We can clear the parser data, because the file will be reparsed + // as soon as it is opened by the user. + + // This will save us some memory, because we only use the + // compilation unit created by the visitor above for code completion. + if (fileContent.Version == null) { + parser.Lock.EnterWriteLock(); + // double-checked locking (other threads might parse the document in the meantime) + if (lastParsedVersion == null) { + parser.Clear(); + } + parser.Lock.ExitWriteLock(); + } + + return compilationUnit; } /// diff --git a/src/AddIns/Debugger/Debugger.AddIn/Pads/CallStackPad.xaml.cs b/src/AddIns/Debugger/Debugger.AddIn/Pads/CallStackPad.xaml.cs index 39e0e41589..682c41aa13 100644 --- a/src/AddIns/Debugger/Debugger.AddIn/Pads/CallStackPad.xaml.cs +++ b/src/AddIns/Debugger/Debugger.AddIn/Pads/CallStackPad.xaml.cs @@ -232,7 +232,7 @@ namespace ICSharpCode.SharpDevelop.Gui.Pads } if (showArgumentValues) { try { - argValue = frame.GetArgumentValue(i).AsString; + argValue = frame.GetArgumentValue(i).AsString(100); } catch { } } if (parameterName != null && argValue != null) { diff --git a/src/AddIns/Debugger/Debugger.AddIn/Service/AttachToProcessForm.cs b/src/AddIns/Debugger/Debugger.AddIn/Service/AttachToProcessForm.cs index 964f35eb3d..e3507a5ec8 100644 --- a/src/AddIns/Debugger/Debugger.AddIn/Service/AttachToProcessForm.cs +++ b/src/AddIns/Debugger/Debugger.AddIn/Service/AttachToProcessForm.cs @@ -5,7 +5,9 @@ using System; using System.ComponentModel; using System.Diagnostics; using System.IO; +using System.Linq; using System.Windows.Forms; + using ICSharpCode.Core; using ICSharpCode.SharpDevelop.Debugging; using ICSharpCode.SharpDevelop.Gui; @@ -23,7 +25,10 @@ namespace ICSharpCode.SharpDevelop.Services { this.process = process; try { - managed = debugger.IsManaged(process.Id); + var modules = process.Modules.Cast().Where( + m => m.ModuleName.StartsWith("mscor", StringComparison.InvariantCultureIgnoreCase)); + + managed = modules.Count() > 0; } catch { } string fileName = Path.GetFileName(process.MainModule.FileName); @@ -54,7 +59,7 @@ namespace ICSharpCode.SharpDevelop.Services { listView.Items.Clear(); WindowsDebugger debugger = (WindowsDebugger)DebuggerService.CurrentDebugger; - Process currentProcess = Process.GetCurrentProcess(); + Process currentProcess = Process.GetCurrentProcess(); foreach (Process process in Process.GetProcesses()) { try { if (process.HasExited) continue; @@ -69,8 +74,8 @@ namespace ICSharpCode.SharpDevelop.Services } catch (Win32Exception) { // Do nothing. } - } + } listView.Sort(); - } + } } } diff --git a/src/AddIns/Debugger/Debugger.AddIn/Service/WindowsDebugger.cs b/src/AddIns/Debugger/Debugger.AddIn/Service/WindowsDebugger.cs index 5e02c124b9..d9a03c0ff7 100644 --- a/src/AddIns/Debugger/Debugger.AddIn/Service/WindowsDebugger.cs +++ b/src/AddIns/Debugger/Debugger.AddIn/Service/WindowsDebugger.cs @@ -382,7 +382,7 @@ namespace ICSharpCode.SharpDevelop.Services try { Value val = GetValueFromName(variableName); if (val == null) return null; - return val.AsString; + return val.AsString(); } catch (GetValueException) { return null; } diff --git a/src/AddIns/Debugger/Debugger.AddIn/TreeModel/ExpressionNode.cs b/src/AddIns/Debugger/Debugger.AddIn/TreeModel/ExpressionNode.cs index 85c59bf3ec..813135904c 100644 --- a/src/AddIns/Debugger/Debugger.AddIn/TreeModel/ExpressionNode.cs +++ b/src/AddIns/Debugger/Debugger.AddIn/TreeModel/ExpressionNode.cs @@ -215,7 +215,7 @@ namespace Debugger.AddIn.TreeModel return; } } else { - fullText = val.AsString; + fullText = val.AsString(); } this.Text = (fullText.Length > 256) ? fullText.Substring(0, 256) + "..." : fullText; diff --git a/src/AddIns/Debugger/Debugger.AddIn/Visualizers/Utils/DebuggerHelpers.cs b/src/AddIns/Debugger/Debugger.AddIn/Visualizers/Utils/DebuggerHelpers.cs index af98c2c42e..165f739a48 100644 --- a/src/AddIns/Debugger/Debugger.AddIn/Visualizers/Utils/DebuggerHelpers.cs +++ b/src/AddIns/Debugger/Debugger.AddIn/Visualizers/Utils/DebuggerHelpers.cs @@ -88,11 +88,11 @@ namespace Debugger.AddIn.Visualizers.Utils // value.InvokeMethod is nice for instance methods. // what about MethodInfo.Invoke() ? // also, there could be an overload that takes 1 parameter instead of array - string defaultHashCode = Eval.InvokeMethod(DebuggerHelpers.hashCodeMethod, null, new Value[]{value}).AsString; + Value defaultHashCode = Eval.InvokeMethod(DebuggerHelpers.hashCodeMethod, null, new Value[]{value}); //MethodInfo method = value.Type.GetMember("GetHashCode", BindingFlags.Method | BindingFlags.IncludeSuperType) as MethodInfo; //string hashCode = value.InvokeMethod(method, null).AsString; - return int.Parse(defaultHashCode); + return (int)defaultHashCode.PrimitiveValue; } public static Value EvalPermanentReference(this Expression expr) diff --git a/src/AddIns/Debugger/Debugger.Core/Exception.cs b/src/AddIns/Debugger/Debugger.Core/Exception.cs index 4153077ab1..ee75897de2 100644 --- a/src/AddIns/Debugger/Debugger.Core/Exception.cs +++ b/src/AddIns/Debugger/Debugger.Core/Exception.cs @@ -33,7 +33,7 @@ namespace Debugger public string Message { get { Value message = exception.GetMemberValue("_message"); - return message.IsNull ? string.Empty : message.AsString; + return message.IsNull ? string.Empty : message.AsString(); } } @@ -86,7 +86,7 @@ namespace Debugger // Note that evaluation is not possible after a stackoverflow exception Value stackTrace = exception.GetMemberValue("StackTrace"); if (!stackTrace.IsNull) { - sb.Append(stackTrace.AsString); + sb.Append(stackTrace.AsString()); sb.AppendLine(); } return sb.ToString(); diff --git a/src/AddIns/Debugger/Debugger.Core/Thread.cs b/src/AddIns/Debugger/Debugger.Core/Thread.cs index 330cb1d9e3..5ad86f2df8 100644 --- a/src/AddIns/Debugger/Debugger.Core/Thread.cs +++ b/src/AddIns/Debugger/Debugger.Core/Thread.cs @@ -156,7 +156,7 @@ namespace Debugger if (runtimeValue.IsNull) return string.Empty; Value runtimeName = runtimeValue.GetMemberValue("m_Name"); if (runtimeName.IsNull) return string.Empty; - return runtimeName.AsString.ToString(); + return runtimeName.AsString(100); } } diff --git a/src/AddIns/Debugger/Debugger.Core/Value.cs b/src/AddIns/Debugger/Debugger.Core/Value.cs index 61985a5cb5..e104f05c19 100644 --- a/src/AddIns/Debugger/Debugger.Core/Value.cs +++ b/src/AddIns/Debugger/Debugger.Core/Value.cs @@ -114,7 +114,7 @@ namespace Debugger public bool IsInvalid { get { return corValue_pauseSession != this.Process.PauseSession && - !(corValue is ICorDebugHandleValue); + !(corValue is ICorDebugHandleValue); } } @@ -149,12 +149,23 @@ namespace Debugger } /// Gets a string representation of the value - public string AsString { - get { - if (this.IsNull) return "null"; - if (this.Type.IsPrimitive) return PrimitiveValue.ToString(); - if (this.Type.FullName == typeof(string).FullName) return PrimitiveValue.ToString(); - return "{" + this.Type.FullName + "}"; + /// + /// The maximum length of the result string. + /// + public string AsString(int maxLength = int.MaxValue) + { + if (this.IsNull) return "null"; + if (this.Type.IsPrimitive || this.Type.FullName == typeof(string).FullName) { + string text = PrimitiveValue.ToString(); + if (text != null && text.Length > maxLength) + text = text.Substring(0, Math.Max(0, maxLength - 3)) + "..."; + return text; + } else { + string name = this.Type.FullName; + if (name != null && name.Length > maxLength) + return "{" + name.Substring(0, Math.Max(0, maxLength - 5)) + "...}"; + else + return "{" + name + "}"; } } @@ -251,7 +262,7 @@ namespace Debugger /// /// If setting of a value fails, NotSupportedException is thrown. /// - public object PrimitiveValue { + public object PrimitiveValue { get { if (this.Type.FullName == typeof(string).FullName) { if (this.IsNull) return null; @@ -302,7 +313,7 @@ namespace Debugger /// eg new object[4,5] returns 2 /// /// 0 for non-arrays - public int ArrayRank { + public int ArrayRank { get { if (!this.Type.IsArray) return 0; return (int)CorArrayValue.GetRank(); @@ -476,7 +487,7 @@ namespace Debugger ICorDebugFrame curFrame = null; if (process.IsPaused && process.SelectedThread != null && - process.SelectedThread.MostRecentStackFrame != null && + process.SelectedThread.MostRecentStackFrame != null && process.SelectedThread.MostRecentStackFrame.CorILFrame != null) { curFrame = process.SelectedThread.MostRecentStackFrame.CorILFrame; @@ -600,14 +611,14 @@ namespace Debugger } /// Invoke the ToString() method - public string InvokeToString() + public string InvokeToString(int maxLength = int.MaxValue) { - if (this.Type.IsPrimitive) return AsString; - if (this.Type.FullName == typeof(string).FullName) return AsString; + if (this.Type.IsPrimitive) return AsString(maxLength); + if (this.Type.FullName == typeof(string).FullName) return AsString(maxLength); if (this.Type.IsPointer) return "0x" + this.PointerAddress.ToString("X"); // if (!IsObject) // Can invoke on primitives DebugMethodInfo methodInfo = (DebugMethodInfo)this.AppDomain.ObjectType.GetMethod("ToString", new DebugType[] {}); - return Eval.InvokeMethod(methodInfo, this, new Value[] {}).AsString; + return Eval.InvokeMethod(methodInfo, this, new Value[] {}).AsString(maxLength); } #region Convenience overload methods @@ -636,9 +647,7 @@ namespace Debugger public override string ToString() { - return this.AsString; + return this.AsString(); } } - - } diff --git a/src/AddIns/Debugger/Debugger.Tests/Tests/AppDomain_Tests.cs b/src/AddIns/Debugger/Debugger.Tests/Tests/AppDomain_Tests.cs index 22684b3201..99b3c792c1 100644 --- a/src/AddIns/Debugger/Debugger.Tests/Tests/AppDomain_Tests.cs +++ b/src/AddIns/Debugger/Debugger.Tests/Tests/AppDomain_Tests.cs @@ -43,7 +43,7 @@ namespace Debugger.Tests { DebugType type1b = process.SelectedStackFrame.GetLocalVariableValue("one").Type; ObjectDump("SameDomainEqual", type1 == type1b); process.Continue(); - ObjectDump("AppDomainName", process.SelectedStackFrame.GetLocalVariableValue("appDomainName").AsString); + ObjectDump("AppDomainName", process.SelectedStackFrame.GetLocalVariableValue("appDomainName").AsString()); DebugType type2 = process.SelectedStackFrame.GetLocalVariableValue("two").Type; ObjectDump("OtherDomainEqual", type1 == type2); ObjectDump("AppDomainsEqual", type1.AppDomain == type2.AppDomain); diff --git a/src/AddIns/Debugger/Debugger.Tests/Tests/ExpressionEvaluator_Tests.cs b/src/AddIns/Debugger/Debugger.Tests/Tests/ExpressionEvaluator_Tests.cs index a649e0cc1e..2aa62276b7 100644 --- a/src/AddIns/Debugger/Debugger.Tests/Tests/ExpressionEvaluator_Tests.cs +++ b/src/AddIns/Debugger/Debugger.Tests/Tests/ExpressionEvaluator_Tests.cs @@ -264,9 +264,9 @@ namespace Debugger.Tests { ObjectDump("TypesIdentitcal", object.ReferenceEquals(locType, valType)); ObjectDump("TypesEqual", locType == valType); - ObjectDump("WorkerThreadMoved", process.SelectedStackFrame.GetThisValue().GetMemberValue("WorkerThreadMoved").AsString); + ObjectDump("WorkerThreadMoved", process.SelectedStackFrame.GetThisValue().GetMemberValue("WorkerThreadMoved").AsString()); process.Continue(); - ObjectDump("WorkerThreadMoved", process.SelectedStackFrame.GetThisValue().GetMemberValue("WorkerThreadMoved").AsString); + ObjectDump("WorkerThreadMoved", process.SelectedStackFrame.GetThisValue().GetMemberValue("WorkerThreadMoved").AsString()); EndTest(); } diff --git a/src/AddIns/Debugger/Debugger.Tests/Tests/StackFrame_VariablesLifetime.cs b/src/AddIns/Debugger/Debugger.Tests/Tests/StackFrame_VariablesLifetime.cs index 3bb9833307..720052911f 100644 --- a/src/AddIns/Debugger/Debugger.Tests/Tests/StackFrame_VariablesLifetime.cs +++ b/src/AddIns/Debugger/Debugger.Tests/Tests/StackFrame_VariablesLifetime.cs @@ -97,26 +97,22 @@ namespace Debugger.Tests { Break StackFrame_VariablesLifetime.cs:21,4-21,40 <_x0040_class> Break StackFrame_VariablesLifetime.cs:30,4-30,40 <_x0040_class> Break StackFrame_VariablesLifetime.cs:23,4-23,40 <_x0040_class> Break StackFrame_VariablesLifetime.cs:30,4-30,40 <_x0040_class> Break StackFrame_VariablesLifetime.cs:15,4-15,40 <_x0040_class> @@ -112,7 +111,6 @@ namespace Debugger.Tests { ArrayDimensions="{2, 2}" ArrayLength="4" ArrayRank="2" - AsString="{System.Int32[,]}" GetArrayElements="{0, 1, 2, 3}" IsReference="True" PrimitiveValue="{Exception: Value is not a primitive type}" @@ -123,7 +121,6 @@ namespace Debugger.Tests { ArrayDimensions="{10..11, 20..21}" ArrayLength="4" ArrayRank="2" - AsString="{System.Char[,]}" GetArrayElements="{a, b, c, d}" IsReference="True" PrimitiveValue="{Exception: Value is not a primitive type}" @@ -131,7 +128,6 @@ namespace Debugger.Tests { diff --git a/src/AddIns/DisplayBindings/AvalonEdit.AddIn/Src/BracketHighlightRenderer.cs b/src/AddIns/DisplayBindings/AvalonEdit.AddIn/Src/BracketHighlightRenderer.cs index 3e2778e723..a7a93b6f89 100644 --- a/src/AddIns/DisplayBindings/AvalonEdit.AddIn/Src/BracketHighlightRenderer.cs +++ b/src/AddIns/DisplayBindings/AvalonEdit.AddIn/Src/BracketHighlightRenderer.cs @@ -2,8 +2,10 @@ // This code is distributed under the GNU LGPL (for details please see \doc\license.txt) using System; +using System.Collections.Generic; using System.Diagnostics; using System.Windows.Media; + using ICSharpCode.AvalonEdit.Document; using ICSharpCode.AvalonEdit.Rendering; using ICSharpCode.SharpDevelop.Editor; @@ -17,6 +19,11 @@ namespace ICSharpCode.AvalonEdit.AddIn Brush backgroundBrush; TextView textView; + public static readonly Color DefaultBackground = Color.FromArgb(22, 0, 0, 255); + public static readonly Color DefaultBorder = Color.FromArgb(52, 0, 0, 255); + + public const string BracketHighlight = "Bracket highlight"; + public void SetHighlight(BracketSearchResult result) { if (this.result != result) { @@ -30,16 +37,19 @@ namespace ICSharpCode.AvalonEdit.AddIn if (textView == null) throw new ArgumentNullException("textView"); - this.borderPen = new Pen(new SolidColorBrush(Color.FromArgb(52, 0, 0, 255)), 1); - this.borderPen.Freeze(); - - this.backgroundBrush = new SolidColorBrush(Color.FromArgb(22, 0, 0, 255)); - this.backgroundBrush.Freeze(); - this.textView = textView; this.textView.BackgroundRenderers.Add(this); } + + void UpdateColors(Color background, Color foreground) + { + this.borderPen = new Pen(new SolidColorBrush(foreground), 1); + this.borderPen.Freeze(); + + this.backgroundBrush = new SolidColorBrush(background); + this.backgroundBrush.Freeze(); + } public KnownLayer Layer { get { @@ -66,5 +76,15 @@ namespace ICSharpCode.AvalonEdit.AddIn drawingContext.DrawGeometry(backgroundBrush, borderPen, geometry); } } + + public static void ApplyCustomizationsToRendering(BracketHighlightRenderer renderer, IEnumerable customizations) + { + renderer.UpdateColors(DefaultBackground, DefaultBorder); + foreach (CustomizedHighlightingColor color in customizations) { + if (color.Name == BracketHighlight) { + renderer.UpdateColors(color.Background ?? Colors.Blue, color.Foreground ?? Colors.Blue); + } + } + } } } diff --git a/src/AddIns/DisplayBindings/AvalonEdit.AddIn/Src/CaretReferencesRenderer.cs b/src/AddIns/DisplayBindings/AvalonEdit.AddIn/Src/CaretReferencesRenderer.cs index 4a72f4c514..72bb3ac568 100644 --- a/src/AddIns/DisplayBindings/AvalonEdit.AddIn/Src/CaretReferencesRenderer.cs +++ b/src/AddIns/DisplayBindings/AvalonEdit.AddIn/Src/CaretReferencesRenderer.cs @@ -3,6 +3,7 @@ using System; using System.Collections.Generic; +using System.Threading; using System.Windows.Threading; using ICSharpCode.AvalonEdit.AddIn.Options; @@ -10,6 +11,7 @@ using ICSharpCode.Core; using ICSharpCode.SharpDevelop; using ICSharpCode.SharpDevelop.Dom; using ICSharpCode.SharpDevelop.Editor; +using ICSharpCode.SharpDevelop.Gui; using ICSharpCode.SharpDevelop.Refactoring; namespace ICSharpCode.AvalonEdit.AddIn @@ -127,10 +129,20 @@ namespace ICSharpCode.AvalonEdit.AddIn /// List GetReferencesInCurrentFile(ResolveResult resolveResult) { - var references = RefactoringService.FindReferencesLocal(resolveResult, Editor.FileName, null); - if (references == null || references.Count == 0) - return null; - return references; + var cancellationTokenSource = new CancellationTokenSource(); + using (new Timer( + delegate { + LoggingService.Debug("Aborting GetReferencesInCurrentFile due to timeout"); + cancellationTokenSource.Cancel(); + }, null, 200, Timeout.Infinite)) + { + var progressMonitor = new DummyProgressMonitor(); + progressMonitor.CancellationToken = cancellationTokenSource.Token; + var references = RefactoringService.FindReferencesLocal(resolveResult, Editor.FileName, progressMonitor); + if (references == null || references.Count == 0) + return null; + return references; + } } /// diff --git a/src/AddIns/DisplayBindings/AvalonEdit.AddIn/Src/CodeEditor.cs b/src/AddIns/DisplayBindings/AvalonEdit.AddIn/Src/CodeEditor.cs index 2146d112ed..57c364d3d6 100644 --- a/src/AddIns/DisplayBindings/AvalonEdit.AddIn/Src/CodeEditor.cs +++ b/src/AddIns/DisplayBindings/AvalonEdit.AddIn/Src/CodeEditor.cs @@ -217,10 +217,11 @@ namespace ICSharpCode.AvalonEdit.AddIn TextCopied(this, e); } - protected virtual void DisposeTextEditor(TextEditor textEditor) + protected virtual void DisposeTextEditor(CodeEditorView textEditor) { // detach IconBarMargin from IconBarManager textEditor.TextArea.LeftMargins.OfType().Single().TextView = null; + textEditor.Dispose(); } void textEditor_GotFocus(object sender, RoutedEventArgs e) @@ -332,9 +333,9 @@ namespace ICSharpCode.AvalonEdit.AddIn // remove secondary editor this.Children.Remove(secondaryTextEditor); this.Children.Remove(gridSplitter); + secondaryTextEditorAdapter.Language.Detach(); DisposeTextEditor(secondaryTextEditor); secondaryTextEditor = null; - secondaryTextEditorAdapter.Language.Detach(); secondaryTextEditorAdapter = null; gridSplitter = null; this.RowDefinitions.RemoveAt(this.RowDefinitions.Count - 1); @@ -574,6 +575,9 @@ namespace ICSharpCode.AvalonEdit.AddIn if (errorPainter != null) errorPainter.Dispose(); this.Document = null; + DisposeTextEditor(primaryTextEditor); + if (secondaryTextEditor != null) + DisposeTextEditor(secondaryTextEditor); } } } diff --git a/src/AddIns/DisplayBindings/AvalonEdit.AddIn/Src/CodeEditorView.cs b/src/AddIns/DisplayBindings/AvalonEdit.AddIn/Src/CodeEditorView.cs index 2875913005..6c38f49666 100755 --- a/src/AddIns/DisplayBindings/AvalonEdit.AddIn/Src/CodeEditorView.cs +++ b/src/AddIns/DisplayBindings/AvalonEdit.AddIn/Src/CodeEditorView.cs @@ -36,7 +36,7 @@ namespace ICSharpCode.AvalonEdit.AddIn /// There can be two CodeEditorView instances in a single CodeEditor if split-view /// is enabled. /// - public class CodeEditorView : SharpDevelopTextEditor + public class CodeEditorView : SharpDevelopTextEditor, IDisposable { public ITextEditor Adapter { get; set; } @@ -48,20 +48,33 @@ namespace ICSharpCode.AvalonEdit.AddIn { this.CommandBindings.Add(new CommandBinding(ApplicationCommands.Help, OnHelpExecuted)); - UpdateCustomizedHighlighting(); - this.bracketRenderer = new BracketHighlightRenderer(this.TextArea.TextView); this.caretReferencesRenderer = new CaretReferencesRenderer(this); this.contextActionsRenderer = new ContextActionsRenderer(this); + UpdateCustomizedHighlighting(); + this.MouseHover += TextEditorMouseHover; this.MouseHoverStopped += TextEditorMouseHoverStopped; this.MouseLeave += TextEditorMouseLeave; this.TextArea.TextView.MouseDown += TextViewMouseDown; this.TextArea.Caret.PositionChanged += HighlightBrackets; + this.TextArea.TextView.VisualLinesChanged += CodeEditorView_VisualLinesChanged; SetupTabSnippetHandler(); } + + void CodeEditorView_VisualLinesChanged(object sender, EventArgs e) + { + // hide tooltip + if (this.toolTip != null) + this.toolTip.IsOpen = false; + } + + public virtual void Dispose() + { + contextActionsRenderer.Dispose(); + } protected override string FileName { get { return this.Adapter.FileName; } @@ -491,6 +504,7 @@ namespace ICSharpCode.AvalonEdit.AddIn { string language = this.SyntaxHighlighting != null ? this.SyntaxHighlighting.Name : null; CustomizableHighlightingColorizer.ApplyCustomizationsToDefaultElements(this, FetchCustomizations(language)); + BracketHighlightRenderer.ApplyCustomizationsToRendering(this.bracketRenderer, FetchCustomizations(language)); this.TextArea.TextView.Redraw(); // manually redraw if default elements didn't change but customized highlightings did } diff --git a/src/AddIns/DisplayBindings/AvalonEdit.AddIn/Src/ContextActionsRenderer.cs b/src/AddIns/DisplayBindings/AvalonEdit.AddIn/Src/ContextActionsRenderer.cs index 1d9f98d0bd..e4c1708ee4 100644 --- a/src/AddIns/DisplayBindings/AvalonEdit.AddIn/Src/ContextActionsRenderer.cs +++ b/src/AddIns/DisplayBindings/AvalonEdit.AddIn/Src/ContextActionsRenderer.cs @@ -18,7 +18,7 @@ namespace ICSharpCode.AvalonEdit.AddIn /// /// Renders Popup with context actions on the left side of the current line in the editor. /// - public class ContextActionsRenderer + public sealed class ContextActionsRenderer : IDisposable { readonly CodeEditorView editorView; ITextEditor Editor { get { return this.editorView.Adapter; } } @@ -36,12 +36,11 @@ namespace ICSharpCode.AvalonEdit.AddIn public bool IsEnabled { get { - try { - string fileName = this.Editor.FileName; - return fileName.EndsWith(".cs") || fileName.EndsWith(".vb"); - } catch { + string fileName = this.Editor.FileName; + if (String.IsNullOrEmpty(fileName)) return false; - } + return fileName.EndsWith(".cs", StringComparison.OrdinalIgnoreCase) + || fileName.EndsWith(".vb", StringComparison.OrdinalIgnoreCase); } } @@ -59,10 +58,16 @@ namespace ICSharpCode.AvalonEdit.AddIn this.delayMoveTimer = new DispatcherTimer() { Interval = TimeSpan.FromMilliseconds(delayMoveMilliseconds) }; this.delayMoveTimer.Stop(); this.delayMoveTimer.Tick += TimerMoveTick; - WorkbenchSingleton.Workbench.ViewClosed += WorkbenchSingleton_Workbench_ViewClosed; WorkbenchSingleton.Workbench.ActiveViewContentChanged += WorkbenchSingleton_Workbench_ActiveViewContentChanged; } - + + public void Dispose() + { + ClosePopup(); + WorkbenchSingleton.Workbench.ActiveViewContentChanged -= WorkbenchSingleton_Workbench_ActiveViewContentChanged; + delayMoveTimer.Stop(); + } + void ContextActionsRenderer_KeyDown(object sender, KeyEventArgs e) { if (this.popup == null) @@ -139,27 +144,14 @@ namespace ICSharpCode.AvalonEdit.AddIn this.lastActions = null; } } - - void WorkbenchSingleton_Workbench_ViewClosed(object sender, ViewContentEventArgs e) - { - try { - // prevent memory leaks - if (e.Content.PrimaryFileName == this.Editor.FileName) { - WorkbenchSingleton.Workbench.ViewClosed -= WorkbenchSingleton_Workbench_ViewClosed; - WorkbenchSingleton.Workbench.ActiveViewContentChanged -= WorkbenchSingleton_Workbench_ActiveViewContentChanged; - ClosePopup(); - } - } catch {} - } - void WorkbenchSingleton_Workbench_ActiveViewContentChanged(object sender, EventArgs e) { - ClosePopup(); - try { - // open the popup again if in current file - if (((IViewContent)WorkbenchSingleton.Workbench.ActiveContent).PrimaryFileName == this.Editor.FileName) - CaretPositionChanged(this, EventArgs.Empty); - } catch {} + // open the popup again if in current file + IViewContent activeViewContent = WorkbenchSingleton.Workbench.ActiveViewContent; + if (activeViewContent != null && activeViewContent.PrimaryFileName == this.Editor.FileName) + CaretPositionChanged(this, EventArgs.Empty); + else // otherwise close popup + ClosePopup(); } } } diff --git a/src/AddIns/DisplayBindings/AvalonEdit.AddIn/Src/CustomizableHighlightingColorizer.cs b/src/AddIns/DisplayBindings/AvalonEdit.AddIn/Src/CustomizableHighlightingColorizer.cs index a7d18c4533..db54de5841 100644 --- a/src/AddIns/DisplayBindings/AvalonEdit.AddIn/Src/CustomizableHighlightingColorizer.cs +++ b/src/AddIns/DisplayBindings/AvalonEdit.AddIn/Src/CustomizableHighlightingColorizer.cs @@ -6,8 +6,8 @@ using System.Collections.Generic; using System.Diagnostics; using System.Linq; using System.Windows; +using System.Windows.Controls; using System.Windows.Media; - using ICSharpCode.AvalonEdit.Document; using ICSharpCode.AvalonEdit.Editing; using ICSharpCode.AvalonEdit.Highlighting; @@ -22,16 +22,23 @@ namespace ICSharpCode.AvalonEdit.AddIn { public const string DefaultTextAndBackground = "Default text/background"; public const string SelectedText = "Selected text"; + public const string NonPrintableCharacters = "Non-printable characters"; + public const string LineNumbers = "Line numbers"; public static void ApplyCustomizationsToDefaultElements(TextEditor textEditor, IEnumerable customizations) { textEditor.ClearValue(TextEditor.BackgroundProperty); textEditor.ClearValue(TextEditor.ForegroundProperty); + textEditor.ClearValue(TextEditor.LineNumbersForegroundProperty); textEditor.TextArea.ClearValue(TextArea.SelectionBorderProperty); textEditor.TextArea.ClearValue(TextArea.SelectionBrushProperty); textEditor.TextArea.ClearValue(TextArea.SelectionForegroundProperty); + textEditor.TextArea.TextView.ClearValue(TextView.NonPrintableCharacterBrushProperty); + bool assignedDefaultText = false; bool assignedSelectedText = false; + bool assignedNonPrintableCharacter = false; + bool assignedLineNumbers = false; foreach (CustomizedHighlightingColor color in customizations) { switch (color.Name) { case DefaultTextAndBackground: @@ -54,7 +61,7 @@ namespace ICSharpCode.AvalonEdit.AddIn pen.Freeze(); textEditor.TextArea.SelectionBorder = pen; SolidColorBrush back = new SolidColorBrush(color.Background.Value); - back.Opacity = 0.7; + back.Opacity = 0.7; // TODO : remove this constant, let the use choose the opacity. back.Freeze(); textEditor.TextArea.SelectionBrush = back; } @@ -62,6 +69,22 @@ namespace ICSharpCode.AvalonEdit.AddIn textEditor.TextArea.SelectionForeground = CreateFrozenBrush(color.Foreground.Value); } break; + case NonPrintableCharacters: + if (assignedNonPrintableCharacter) + continue; + assignedNonPrintableCharacter = true; + + if (color.Foreground != null) + textEditor.TextArea.TextView.NonPrintableCharacterBrush = CreateFrozenBrush(color.Foreground.Value); + break; + case LineNumbers: + if (assignedLineNumbers) + continue; + assignedLineNumbers = true; + + if (color.Foreground != null) + textEditor.LineNumbersForeground = CreateFrozenBrush(color.Foreground.Value); + break; } } } diff --git a/src/AddIns/DisplayBindings/AvalonEdit.AddIn/Src/Options/HighlightingOptions.xaml.cs b/src/AddIns/DisplayBindings/AvalonEdit.AddIn/Src/Options/HighlightingOptions.xaml.cs index 35331c84a5..20b1836244 100644 --- a/src/AddIns/DisplayBindings/AvalonEdit.AddIn/Src/Options/HighlightingOptions.xaml.cs +++ b/src/AddIns/DisplayBindings/AvalonEdit.AddIn/Src/Options/HighlightingOptions.xaml.cs @@ -10,11 +10,13 @@ using System.Windows; using System.Windows.Controls; using System.Windows.Media; using System.Xml; - using ICSharpCode.AvalonEdit.Editing; using ICSharpCode.AvalonEdit.Highlighting; using ICSharpCode.AvalonEdit.Highlighting.Xshd; using ICSharpCode.AvalonEdit.Rendering; +using ICSharpCode.SharpDevelop.Bookmarks; +using ICSharpCode.SharpDevelop.Editor; +using ICSharpCode.SharpDevelop.Editor.AvalonEdit; using ICSharpCode.SharpDevelop.Gui; namespace ICSharpCode.AvalonEdit.AddIn.Options @@ -29,9 +31,13 @@ namespace ICSharpCode.AvalonEdit.AddIn.Options InitializeComponent(); textEditor.Document.UndoStack.SizeLimit = 0; textEditor.Options = CodeEditorOptions.Instance; + bracketHighlighter = new BracketHighlightRenderer(textEditor.TextArea.TextView); + CodeEditorOptions.Instance.BindToTextEditor(textEditor); } + BracketHighlightRenderer bracketHighlighter; + List customizationList; XshdSyntaxDefinition LoadBuiltinXshd(string name) @@ -132,6 +138,61 @@ namespace ICSharpCode.AvalonEdit.AddIn.Options selectedText = new CustomizedHighlightingItem(customizationList, selectedText, language, canSetFont: false); selectedText.PropertyChanged += item_PropertyChanged; listBox.Items.Add(selectedText); + + // Create entry for "Non-printable characters" + IHighlightingItem nonPrintChars = new SimpleHighlightingItem( + CustomizableHighlightingColorizer.NonPrintableCharacters, + ta => { + ta.Document.Text = " \r \r\n \n"; + }) + { + Foreground = Colors.LightGray + }; + nonPrintChars = new CustomizedHighlightingItem(customizationList, nonPrintChars, null, canSetFont: false, canSetBackground: false); + if (language != null) + nonPrintChars = new CustomizedHighlightingItem(customizationList, nonPrintChars, language, canSetFont: false); + nonPrintChars.PropertyChanged += item_PropertyChanged; + listBox.Items.Add(nonPrintChars); + + // Create entry for "Line numbers" + IHighlightingItem lineNumbers = new SimpleHighlightingItem( + CustomizableHighlightingColorizer.LineNumbers, + ta => { + ta.Document.Text = "These are just" + Environment.NewLine + + "multiple" + Environment.NewLine + + "lines of" + Environment.NewLine + + "text"; + }) + { + Foreground = Colors.Gray + }; + lineNumbers = new CustomizedHighlightingItem(customizationList, lineNumbers, null, canSetFont: false, canSetBackground: false); + if (language != null) + lineNumbers = new CustomizedHighlightingItem(customizationList, lineNumbers, language, canSetFont: false); + lineNumbers.PropertyChanged += item_PropertyChanged; + listBox.Items.Add(lineNumbers); + + // Create entry for "Bracket highlight" + IHighlightingItem bracketHighlight = new SimpleHighlightingItem( + BracketHighlightRenderer.BracketHighlight, + ta => { + ta.Document.Text = "(simple) example"; + XshdSyntaxDefinition xshd = (XshdSyntaxDefinition)languageComboBox.SelectedItem; + if (xshd == null) + return; + var customizationsForCurrentLanguage = customizationList.Where(c => c.Language == null || c.Language == xshd.Name); + BracketHighlightRenderer.ApplyCustomizationsToRendering(bracketHighlighter, customizationsForCurrentLanguage); + bracketHighlighter.SetHighlight(new BracketSearchResult(0, 1, 7, 1)); + }) + { + Foreground = BracketHighlightRenderer.DefaultBorder, + Background = BracketHighlightRenderer.DefaultBackground + }; + bracketHighlight = new CustomizedHighlightingItem(customizationList, bracketHighlight, null, canSetFont: false); + if (language != null) + bracketHighlight = new CustomizedHighlightingItem(customizationList, bracketHighlight, language, canSetFont: false); + bracketHighlight.PropertyChanged += item_PropertyChanged; + listBox.Items.Add(bracketHighlight); } void item_PropertyChanged(object sender, PropertyChangedEventArgs e) @@ -175,6 +236,7 @@ namespace ICSharpCode.AvalonEdit.AddIn.Options textView.LineTransformers.Add(colorizer); } textEditor.Select(0, 0); + bracketHighlighter.SetHighlight(null); item.ShowExample(textEditor.TextArea); } } diff --git a/src/AddIns/DisplayBindings/WpfDesign/WpfDesign.Designer/Project/Controls/GridAdorner.cs b/src/AddIns/DisplayBindings/WpfDesign/WpfDesign.Designer/Project/Controls/GridAdorner.cs index 53aee95b0e..23a5f166ae 100644 --- a/src/AddIns/DisplayBindings/WpfDesign/WpfDesign.Designer/Project/Controls/GridAdorner.cs +++ b/src/AddIns/DisplayBindings/WpfDesign/WpfDesign.Designer/Project/Controls/GridAdorner.cs @@ -433,34 +433,37 @@ namespace ICSharpCode.WpfDesign.Designer.Controls public void SetGridLengthUnit(GridUnitType unit) { DesignItem item = unitSelector.SelectedItem; - GridLength value; - grid.UpdateLayout(); Debug.Assert(item != null); if (orientation == Orientation.Vertical) { - value = (GridLength)item.Properties[RowDefinition.HeightProperty].ValueOnInstance; - - if (unit == GridUnitType.Auto) - value = GridLength.Auto; - else - value = new GridLength(value.Value, unit); - - item.Properties[RowDefinition.HeightProperty].SetValue(value); + SetGridLengthUnit(unit, item, RowDefinition.HeightProperty); } else { - value = (GridLength)item.Properties[ColumnDefinition.WidthProperty].ValueOnInstance; - - if (unit == GridUnitType.Auto) - value = GridLength.Auto; - else - value = new GridLength(value.Value, unit); - - item.Properties[ColumnDefinition.WidthProperty].SetValue(value); + SetGridLengthUnit(unit, item, ColumnDefinition.WidthProperty); } grid.UpdateLayout(); InvalidateVisual(); } + + void SetGridLengthUnit(GridUnitType unit, DesignItem item, DependencyProperty property) + { + DesignItemProperty itemProperty = item.Properties[property]; + GridLength oldValue = (GridLength)itemProperty.ValueOnInstance; + GridLength value = GetNewGridLength(unit, oldValue); + + if (value != oldValue) { + itemProperty.SetValue(value); + } + } + + GridLength GetNewGridLength(GridUnitType unit, GridLength oldValue) + { + if (unit == GridUnitType.Auto) { + return GridLength.Auto; + } + return new GridLength(oldValue.Value, unit); + } } public abstract class GridSplitterAdorner : Control diff --git a/src/AddIns/DisplayBindings/WpfDesign/WpfDesign.Designer/Project/PropertyGrid/Editors/BrushEditor/SolidBrushEditor.xaml b/src/AddIns/DisplayBindings/WpfDesign/WpfDesign.Designer/Project/PropertyGrid/Editors/BrushEditor/SolidBrushEditor.xaml index dadf1edc74..3a5fffea09 100644 --- a/src/AddIns/DisplayBindings/WpfDesign/WpfDesign.Designer/Project/PropertyGrid/Editors/BrushEditor/SolidBrushEditor.xaml +++ b/src/AddIns/DisplayBindings/WpfDesign/WpfDesign.Designer/Project/PropertyGrid/Editors/BrushEditor/SolidBrushEditor.xaml @@ -1,14 +1,12 @@ - + Height="284"> - + BrushTypeEditor.xaml - - - ColorPicker.xaml - GradientBrushEditor.xaml @@ -176,7 +172,6 @@ GradientSlider.xaml - SolidBrushEditor.xaml @@ -279,10 +274,6 @@ MSBuild:Compile Designer - - MSBuild:Compile - Designer - MSBuild:Compile Designer diff --git a/src/AddIns/DisplayBindings/WpfDesign/WpfDesign.XamlDom/Project/XamlDocument.cs b/src/AddIns/DisplayBindings/WpfDesign/WpfDesign.XamlDom/Project/XamlDocument.cs index df9a2b40af..5b62424e57 100644 --- a/src/AddIns/DisplayBindings/WpfDesign/WpfDesign.XamlDom/Project/XamlDocument.cs +++ b/src/AddIns/DisplayBindings/WpfDesign/WpfDesign.XamlDom/Project/XamlDocument.cs @@ -44,22 +44,24 @@ namespace ICSharpCode.WpfDesign.XamlDom /// type descriptor context needs to resolve an XML namespace. internal ITypeDescriptorContext GetTypeDescriptorContext(XamlObject containingObject) { - return new DummyTypeDescriptorContext(this, containingObject); + IServiceProvider serviceProvider; + if (containingObject != null) { + if (containingObject.OwnerDocument != this) + throw new ArgumentException("Containing object must belong to the document!"); + serviceProvider = containingObject.ServiceProvider; + } else { + serviceProvider = this.ServiceProvider; + } + return new DummyTypeDescriptorContext(serviceProvider); } sealed class DummyTypeDescriptorContext : ITypeDescriptorContext { - IServiceProvider baseServiceProvider; + readonly IServiceProvider baseServiceProvider; - public DummyTypeDescriptorContext(XamlDocument document, XamlObject containingObject) + public DummyTypeDescriptorContext(IServiceProvider serviceProvider) { - if (containingObject != null) { - if (containingObject.OwnerDocument != document) - throw new ArgumentException("Containing object must belong to the document!"); - baseServiceProvider = containingObject.ServiceProvider; - } else { - baseServiceProvider = document.ServiceProvider; - } + this.baseServiceProvider = serviceProvider; } public IContainer Container { @@ -67,7 +69,7 @@ namespace ICSharpCode.WpfDesign.XamlDom } public object Instance { - get { return null; } + get; set; } public PropertyDescriptor PropertyDescriptor { @@ -157,10 +159,11 @@ namespace ICSharpCode.WpfDesign.XamlDom Type elementType = instance.GetType(); TypeConverter c = TypeDescriptor.GetConverter(instance); - bool hasStringConverter = c.CanConvertTo(typeof(string)) && c.CanConvertFrom(typeof(string)); - + var ctx = new DummyTypeDescriptorContext(this.ServiceProvider); + ctx.Instance = instance; + bool hasStringConverter = c.CanConvertTo(ctx, typeof(string)) && c.CanConvertFrom(typeof(string)); if (forProperty != null && hasStringConverter) { - return new XamlTextValue(this, c.ConvertToInvariantString(instance)); + return new XamlTextValue(this, c.ConvertToInvariantString(ctx, instance)); } diff --git a/src/AddIns/Misc/SearchAndReplace/Project/Engine/SearchReplaceManager.cs b/src/AddIns/Misc/SearchAndReplace/Project/Engine/SearchReplaceManager.cs index a7855b4594..1a6a83cde1 100644 --- a/src/AddIns/Misc/SearchAndReplace/Project/Engine/SearchReplaceManager.cs +++ b/src/AddIns/Misc/SearchAndReplace/Project/Engine/SearchReplaceManager.cs @@ -215,7 +215,7 @@ namespace SearchAndReplace if (textArea != null) { string transformedPattern = result.TransformReplacePattern(SearchOptions.ReplacePattern); find.Replace(result.Offset, result.Length, transformedPattern); - if (!find.CurrentDocumentInformation.IsDocumentCreated) { + if (find.CurrentDocumentInformation.IsDocumentCreatedFromTextBuffer) { textArea.Document.Replace(result.Offset, result.Length, transformedPattern); } } else { diff --git a/src/Libraries/AvalonEdit/ICSharpCode.AvalonEdit/CodeCompletion/CompletionList.cs b/src/Libraries/AvalonEdit/ICSharpCode.AvalonEdit/CodeCompletion/CompletionList.cs index e4089e66f6..d9fe15041b 100644 --- a/src/Libraries/AvalonEdit/ICSharpCode.AvalonEdit/CodeCompletion/CompletionList.cs +++ b/src/Libraries/AvalonEdit/ICSharpCode.AvalonEdit/CodeCompletion/CompletionList.cs @@ -326,31 +326,31 @@ namespace ICSharpCode.AvalonEdit.CodeCompletion // -1 = no match if (query == itemText) return 8; - if (string.Equals(itemText, query, StringComparison.OrdinalIgnoreCase)) + if (string.Equals(itemText, query, StringComparison.InvariantCultureIgnoreCase)) return 7; - if (itemText.StartsWith(query, StringComparison.Ordinal)) + if (itemText.StartsWith(query, StringComparison.InvariantCulture)) return 6; - if (itemText.StartsWith(query, StringComparison.OrdinalIgnoreCase)) + if (itemText.StartsWith(query, StringComparison.InvariantCultureIgnoreCase)) return 5; bool? camelCaseMatch = null; if (query.Length <= 2) { camelCaseMatch = CamelCaseMatch(itemText, query); - if (camelCaseMatch.GetValueOrDefault(false)) return 4; + if (camelCaseMatch == true) return 4; } // search by substring, if filtering (i.e. new behavior) turned on if (IsFiltering) { - if (itemText.Contains(query)) + if (itemText.IndexOf(query, StringComparison.InvariantCulture) >= 0) return 3; - if (itemText.IndexOf(query, StringComparison.OrdinalIgnoreCase) >= 0) + if (itemText.IndexOf(query, StringComparison.InvariantCultureIgnoreCase) >= 0) return 2; } if (!camelCaseMatch.HasValue) camelCaseMatch = CamelCaseMatch(itemText, query); - if (camelCaseMatch.GetValueOrDefault(false)) + if (camelCaseMatch == true) return 1; return -1; diff --git a/src/Libraries/AvalonEdit/ICSharpCode.AvalonEdit/CodeCompletion/CompletionWindow.cs b/src/Libraries/AvalonEdit/ICSharpCode.AvalonEdit/CodeCompletion/CompletionWindow.cs index 351c026e51..95b113d516 100644 --- a/src/Libraries/AvalonEdit/ICSharpCode.AvalonEdit/CodeCompletion/CompletionWindow.cs +++ b/src/Libraries/AvalonEdit/ICSharpCode.AvalonEdit/CodeCompletion/CompletionWindow.cs @@ -48,8 +48,6 @@ namespace ICSharpCode.AvalonEdit.CodeCompletion toolTip.Placement = PlacementMode.Right; toolTip.Closed += toolTip_Closed; - completionList.InsertionRequested += completionList_InsertionRequested; - completionList.SelectionChanged += completionList_SelectionChanged; AttachEvents(); } @@ -98,6 +96,8 @@ namespace ICSharpCode.AvalonEdit.CodeCompletion void AttachEvents() { + this.completionList.InsertionRequested += completionList_InsertionRequested; + this.completionList.SelectionChanged += completionList_SelectionChanged; this.TextArea.Caret.PositionChanged += CaretPositionChanged; this.TextArea.MouseWheel += textArea_MouseWheel; this.TextArea.PreviewTextInput += textArea_PreviewTextInput; @@ -106,6 +106,8 @@ namespace ICSharpCode.AvalonEdit.CodeCompletion /// protected override void DetachEvents() { + this.completionList.InsertionRequested -= completionList_InsertionRequested; + this.completionList.SelectionChanged -= completionList_SelectionChanged; this.TextArea.Caret.PositionChanged -= CaretPositionChanged; this.TextArea.MouseWheel -= textArea_MouseWheel; this.TextArea.PreviewTextInput -= textArea_PreviewTextInput; diff --git a/src/Libraries/AvalonEdit/ICSharpCode.AvalonEdit/CodeCompletion/CompletionWindowBase.cs b/src/Libraries/AvalonEdit/ICSharpCode.AvalonEdit/CodeCompletion/CompletionWindowBase.cs index 0ad375b8e6..d8a6beb058 100644 --- a/src/Libraries/AvalonEdit/ICSharpCode.AvalonEdit/CodeCompletion/CompletionWindowBase.cs +++ b/src/Libraries/AvalonEdit/ICSharpCode.AvalonEdit/CodeCompletion/CompletionWindowBase.cs @@ -5,9 +5,9 @@ using System; using System.Linq; using System.Diagnostics; using System.Windows; +using System.Windows.Controls.Primitives; using System.Windows.Input; using System.Windows.Threading; - using ICSharpCode.AvalonEdit.Document; using ICSharpCode.AvalonEdit.Editing; using ICSharpCode.AvalonEdit.Rendering; @@ -159,7 +159,13 @@ namespace ICSharpCode.AvalonEdit.CodeCompletion void TextViewScrollOffsetChanged(object sender, EventArgs e) { - UpdatePosition(); + IScrollInfo scrollInfo = this.TextArea.TextView; + Rect visibleRect = new Rect(scrollInfo.HorizontalOffset, scrollInfo.VerticalOffset, scrollInfo.ViewportWidth, scrollInfo.ViewportHeight); + // close completion window when the user scrolls so far that the anchor position is leaving the visible area + if (visibleRect.Contains(visualLocation) || visibleRect.Contains(visualLocationTop)) + UpdatePosition(); + else + Close(); } void TextAreaDocumentChanged(object sender, EventArgs e) diff --git a/src/Libraries/AvalonEdit/ICSharpCode.AvalonEdit/Document/TextDocument.cs b/src/Libraries/AvalonEdit/ICSharpCode.AvalonEdit/Document/TextDocument.cs index 00e2c0c25e..e2db61ef12 100644 --- a/src/Libraries/AvalonEdit/ICSharpCode.AvalonEdit/Document/TextDocument.cs +++ b/src/Libraries/AvalonEdit/ICSharpCode.AvalonEdit/Document/TextDocument.cs @@ -722,13 +722,23 @@ namespace ICSharpCode.AvalonEdit.Document } } - readonly UndoStack undoStack; + UndoStack undoStack; /// /// Gets the of the document. /// + /// This property can also be used to set the undo stack, e.g. for sharing a common undo stack between multiple documents. public UndoStack UndoStack { get { return undoStack; } + set { + if (value == null) + throw new ArgumentNullException(); + if (value != undoStack) { + undoStack.ClearAll(); // first clear old undo stack, so that it can't be used to perform unexpected changes on this document + // ClearAll() will also throw an exception when it's not safe to replace the undo stack (e.g. update is currently in progress) + undoStack = value; + } + } } /// diff --git a/src/Libraries/AvalonEdit/ICSharpCode.AvalonEdit/Editing/DottedLineMargin.cs b/src/Libraries/AvalonEdit/ICSharpCode.AvalonEdit/Editing/DottedLineMargin.cs index 7408e28865..d19791d500 100644 --- a/src/Libraries/AvalonEdit/ICSharpCode.AvalonEdit/Editing/DottedLineMargin.cs +++ b/src/Libraries/AvalonEdit/ICSharpCode.AvalonEdit/Editing/DottedLineMargin.cs @@ -3,6 +3,7 @@ using System; using System.Windows; +using System.Windows.Data; using System.Windows.Media; using System.Windows.Shapes; @@ -19,18 +20,24 @@ namespace ICSharpCode.AvalonEdit.Editing /// /// Creates a vertical dotted line to separate the line numbers from the text view. /// - public static UIElement Create() + public static UIElement Create(TextEditor editor) { - return new Line { + Line line = new Line { X1 = 0, Y1 = 0, X2 = 0, Y2 = 1, StrokeDashArray = { 0, 2 }, Stretch = Stretch.Fill, - Stroke = Brushes.Gray, StrokeThickness = 1, StrokeDashCap = PenLineCap.Round, Margin = new Thickness(2, 0, 2, 0), Tag = tag }; + + line.SetBinding( + Line.StrokeProperty, + new Binding("LineNumbersForeground") { Source = editor } + ); + + return line; } /// diff --git a/src/Libraries/AvalonEdit/ICSharpCode.AvalonEdit/Highlighting/Resources/ASPX.xshd b/src/Libraries/AvalonEdit/ICSharpCode.AvalonEdit/Highlighting/Resources/ASPX.xshd index b101156cc6..f780a5843e 100644 --- a/src/Libraries/AvalonEdit/ICSharpCode.AvalonEdit/Highlighting/Resources/ASPX.xshd +++ b/src/Libraries/AvalonEdit/ICSharpCode.AvalonEdit/Highlighting/Resources/ASPX.xshd @@ -1,13 +1,16 @@ - - - - - <% - %> - - - - - + + + + + + + <% + %> + + + + + + diff --git a/src/Libraries/AvalonEdit/ICSharpCode.AvalonEdit/Highlighting/Resources/CPP-Mode.xshd b/src/Libraries/AvalonEdit/ICSharpCode.AvalonEdit/Highlighting/Resources/CPP-Mode.xshd index 09c1a6a497..f552ad4136 100644 --- a/src/Libraries/AvalonEdit/ICSharpCode.AvalonEdit/Highlighting/Resources/CPP-Mode.xshd +++ b/src/Libraries/AvalonEdit/ICSharpCode.AvalonEdit/Highlighting/Resources/CPP-Mode.xshd @@ -1,236 +1,195 @@ - - - - - - - - - - - - - ~!%^*()-+=|\#/{}[]:;"'<> , .? - - - # - - - - // - - - - /* - */ - - - - " - " - - - - ' - ' - - - ( - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - + + + + + + + + + + + + + + + + + + + + + + + + + + [?,.;()\[\]{}+\-/%*<>^=~!&]+ + + + __abstract + __box + __delegate + __gc + __identifier + __nogc + __pin + __property + __sealed + __try_cast + __typeof + __value + __event + __hook + __raise + __unhook + __interface + ref class + ref struct + value class + value struct + interface class + interface struct + enum class + enum struct + delegate + event + property + abstract + override + sealed + generic + where + finally + for each + gcnew + in + initonly + literal + nullptr + + + this + + + and + and_eq + bitand + bitor + new + not + not_eq + or + or_eq + xor + xor_eq + + + using + namespace + + + friend + + + private + protected + public + const + volatile + static + + + bool + char + unsigned + union + virtual + double + float + short + signed + void + class + enum + struct + + + false + true + + + do + for + while + + + break + continue + goto + return + + + catch + throw + try + + + case + else + if + switch + default + + + asm + auto + compl + mutable + const_cast + delete + dynamic_cast + explicit + export + extern + inline + int + long + operator + register + reinterpret_cast + sizeof + static_cast + template + typedef + typeid + typename + + + \# + + + // + + + /\* + \*/ + + + " + " + + + + + + ' + ' + + + + + [\d\w_]+(?=(\s*\()) + \b0[xX][0-9a-fA-F]+|(\b\d+(\.[0-9]+)?|\.[0-9]+)([eE][+-]?[0-9]+)? + + \ No newline at end of file diff --git a/src/Libraries/AvalonEdit/ICSharpCode.AvalonEdit/Highlighting/Resources/Coco-Mode.xshd b/src/Libraries/AvalonEdit/ICSharpCode.AvalonEdit/Highlighting/Resources/Coco-Mode.xshd index 0eb3b93930..9395198b52 100644 --- a/src/Libraries/AvalonEdit/ICSharpCode.AvalonEdit/Highlighting/Resources/Coco-Mode.xshd +++ b/src/Libraries/AvalonEdit/ICSharpCode.AvalonEdit/Highlighting/Resources/Coco-Mode.xshd @@ -1,97 +1,74 @@ - - - - - - - &<>~!@%^*()-+=|\#/{}[]:;"' , .? - - - // - - - - /* - */ - - - - - COMPILER - TOKENNAMES - - - - " - " - - - - ' - ' - - - - < - > - - - - (. - .) - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - + + + + + + + + + [{}\(\)\[\]|+\-=\.]+ + + + ANY + CHARACTERS + COMMENTS + COMPILER + CONTEXT + END + FROM + IF + IGNORE + NAMESPACE + NESTED + PRAGMAS + PRODUCTIONS + SYNC + TO + TOKENS + TOKENNAMES + WEAK + using + + + // + + + /\* + \*/ + + + COMPILER + TOKENNAMES + + + " + " + + + ' + ' + + + < + > + + + \(\. + \.\) + + \b0[xX][0-9a-fA-F]+|(\b\d+(\.[0-9]+)?|\.[0-9]+)([eE][+-]?[0-9]+)? + + + + \b0[xX][0-9a-fA-F]+|(\b\d+(\.[0-9]+)?|\.[0-9]+)([eE][+-]?[0-9]+)? + + + + \b0[xX][0-9a-fA-F]+|(\b\d+(\.[0-9]+)?|\.[0-9]+)([eE][+-]?[0-9]+)? + + + \b0[xX][0-9a-fA-F]+|(\b\d+(\.[0-9]+)?|\.[0-9]+)([eE][+-]?[0-9]+)? + + \ No newline at end of file diff --git a/src/Libraries/AvalonEdit/ICSharpCode.AvalonEdit/Highlighting/Resources/HTML-Mode.xshd b/src/Libraries/AvalonEdit/ICSharpCode.AvalonEdit/Highlighting/Resources/HTML-Mode.xshd index 5ca4ec47ac..e23d6a624d 100644 --- a/src/Libraries/AvalonEdit/ICSharpCode.AvalonEdit/Highlighting/Resources/HTML-Mode.xshd +++ b/src/Libraries/AvalonEdit/ICSharpCode.AvalonEdit/Highlighting/Resources/HTML-Mode.xshd @@ -1,385 +1,384 @@ - - - - - - - - - - - - - <!-- - --> - - - <script> - </script> - - - <script lang="JavaScript"> - </script> - - - <script lang="JScript"> - </script> - - - <script lang="VBScript"> - </script> - - - <script@C - </script> - - - < - > - - - - & - ; - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - /= - - - " - " - - - - ' - ' - - - = - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - + + + + + + + + + + + + + + + + + + + + + <!-- + --> + + + <script> + </script> + + + <script\ lang="JavaScript"> + </script> + + + <script\ lang="JScript"> + </script> + + + <script\ lang="VBScript"> + </script> + + + <script[^\w\d_] + </script> + + + < + > + + + & + ; + + \b0[xX][0-9a-fA-F]+|(\b\d+(\.[0-9]+)?|\.[0-9]+)([eE][+-]?[0-9]+)? + + + + \b0[xX][0-9a-fA-F]+|(\b\d+(\.[0-9]+)?|\.[0-9]+)([eE][+-]?[0-9]+)? + + + + aacute + agrave + acirc + amp + atilde + aring + auml + aelig + ccedil + copy + eacute + egrave + ecirc + euml + iacute + igrave + icirc + iuml + eth + gt + lt + nbsp + ntilde + oacute + ograve + ocirc + otilde + ouml + oslash + quot + reg + szlig + uacute + ugrave + ucirc + uuml + yacute + thorn + trade + yuml + + \b0[xX][0-9a-fA-F]+|(\b\d+(\.[0-9]+)?|\.[0-9]+)([eE][+-]?[0-9]+)? + + + + / + + + = + + + !DOCTYPE + A + ABBR + ACRONYM + ADDRESS + APPLET + AREA + B + BASE + BASEFONT + BGSOUND + BDO + BIG + BLINK + BLOCKQUOTE + BODY + BR + BUTTON + CAPTION + CENTER + CITE + CODE + COL + COLGROUP + COMMENT + DD + DEL + DFN + DIR + DIV + DL + DT + EM + EMBED + FIELDSET + FONT + FORM + FRAME + FRAMESET + H + H1 + H2 + H3 + H4 + H5 + H6 + HEAD + HR + HTA:APPLICATION + HTML + I + IFRAME + IMG + INPUT + INS + ISINDEX + KBD + LABEL + LEGEnd + LI + LINK + LISTING + MAP + MARQUEE + MENU + META + MULTICOL + NEXTID + NOBR + NOFRAMES + NOSCRIPT + OBJECT + OL + OPTGROUP + OPTION + P + PARAM + PLAINTEXT + PRE + Q + S + SAMP + SCRIPT + SELECT + SERVER + SMALL + SOUND + SPACER + Span + STRONG + STYLE + SUB + SUP + TABLE + TBODY + TD + TEXTAREA + TEXTFLOW + TFOOT + TH + THEAD + TITLE + TR + TT + U + VAR + WBR + XMP + + + abbr + accept-charset + accept + accesskey + action + align + alink + alt + applicationname + archive + axis + background + behavior + bgcolor + bgproperties + border + bordercolor + bordercolordark + bordercolorligh + borderstyle + caption + cellpadding + cellspacing + char + charoff + charset + checked + cite + class + classid + clear + code + codetype + color + cols + colspan + compact + content + coords + data + datetime + declare + defer + dir + direction + disabled + dynsrc + enctype + face + for + frame + frameborder + framespacing + gutter + headers + height + href + hreflang + hspace + http-equiv + icon + id + ismap + label + language + leftmargin + link + longdesc + loop + lowsrc + marginheight + marginwidth + maximizebutton + maxlength + media + method + methods + minimizebutton + multiple + name + nohref + noresize + noshade + nowrap + object + onabort + onblur + onchange + onclick + ondblclick + onerror + onfocus + onkeydown + onkeypress + onkeyup + onload + onmousedown + onmousemove + onmouseout + onmouseover + onmouseup + onreset + onselect + onsubmit + onunload + profile + prompt + readonly + rel + rev + rows + rowspan + rules + runat + scheme + scope + scrollamount + scrolldelay + scrolling + selected + shape + showintaskbar + singleinstance + size + span + src + standby + start + style + summary + sysmenu + tabindex + target + text + title + topmargin + type + urn + usemap + valign + value + valuetype + version + vlink + vrml + vspace + width + windowstate + wrap + + + " + " + + + ' + ' + + [\d\w_]+(?=(\s*=)) + \b0[xX][0-9a-fA-F]+|(\b\d+(\.[0-9]+)?|\.[0-9]+)([eE][+-]?[0-9]+)? + + \ No newline at end of file diff --git a/src/Libraries/AvalonEdit/ICSharpCode.AvalonEdit/Highlighting/Resources/Java-Mode.xshd b/src/Libraries/AvalonEdit/ICSharpCode.AvalonEdit/Highlighting/Resources/Java-Mode.xshd index 913d16e95c..dd5053e911 100644 --- a/src/Libraries/AvalonEdit/ICSharpCode.AvalonEdit/Highlighting/Resources/Java-Mode.xshd +++ b/src/Libraries/AvalonEdit/ICSharpCode.AvalonEdit/Highlighting/Resources/Java-Mode.xshd @@ -1,180 +1,152 @@ - - - - - - - - - - - - - ~!%^*()-+=|\#/{}[]:;"'<> , .? - - - // - - - - /* - */ - - - - " - " - - - - ' - ' - - - ( - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - ~!%^*()-+=|\#/{}[]:;"'<> , .? - - - - - - - - - - - - - - - - - - - - - - - + + + + + + + + + + + + + + + + + + + + + + + + + + [?,.()\[\]{}+\-/%*<>^!|]+ + + + this + super + + + new + instanceof + true + false + + + else + if + switch + case + + + do + for + while + + + break + continue + default + goto + return + + + try + throw + catch + finally + + + boolean + double + int + short + long + float + byte + char + + + class + interface + object + + + void + + + abstract + const + static + final + native + extends + implements + volatile + transient + throws + strictfp + synchronized + + + public + protected + private + + + package + import + + + null + + + // + + + /\* + \*/ + + + " + " + + + + + + ' + ' + + + + + [\d\w_]+(?=(\s*\()) + \b0[xX][0-9a-fA-F]+|(\b\d+(\.[0-9]+)?|\.[0-9]+)([eE][+-]?[0-9]+)? + + + + TODO + + + @author + @version + @param + @return + @exception + @throws + @see + @since + @serial + @serialField + @serialData + @deprecated + + \b0[xX][0-9a-fA-F]+|(\b\d+(\.[0-9]+)?|\.[0-9]+)([eE][+-]?[0-9]+)? + + \ No newline at end of file diff --git a/src/Libraries/AvalonEdit/ICSharpCode.AvalonEdit/Highlighting/Resources/JavaScript-Mode.xshd b/src/Libraries/AvalonEdit/ICSharpCode.AvalonEdit/Highlighting/Resources/JavaScript-Mode.xshd index 23a4708021..59556e4942 100644 --- a/src/Libraries/AvalonEdit/ICSharpCode.AvalonEdit/Highlighting/Resources/JavaScript-Mode.xshd +++ b/src/Libraries/AvalonEdit/ICSharpCode.AvalonEdit/Highlighting/Resources/JavaScript-Mode.xshd @@ -1,136 +1,123 @@ - - - - - - - - - - - - =!><+-/*%&|^~.}{,;][?: - - - // - - - - /* - */ - - - - " - " - - - - ' - ' - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - + + + + + + + + + + + + + break + continue + delete + else + for + function + if + in + new + return + this + typeof + var + void + while + with + abstract + boolean + byte + case + catch + char + class + const + debugger + default + do + double + enum + export + extends + final + finally + float + goto + implements + import + instanceof + int + interface + long + native + package + private + protected + public + short + static + super + switch + synchronized + throw + throws + transient + try + volatile + + + Array + Boolean + Date + Function + Global + Math + Number + Object + RegExp + String + + + false + null + true + NaN + Infinity + + + eval + parseInt + parseFloat + escape + unescape + isNaN + isFinite + + + // + + + /\* + \*/ + + + " + " + + + + + + ' + ' + + + + + \b0[xX][0-9a-fA-F]+|(\b\d+(\.[0-9]+)?|\.[0-9]+)([eE][+-]?[0-9]+)? + + \ No newline at end of file diff --git a/src/Libraries/AvalonEdit/ICSharpCode.AvalonEdit/Highlighting/Resources/PHP-Mode.xshd b/src/Libraries/AvalonEdit/ICSharpCode.AvalonEdit/Highlighting/Resources/PHP-Mode.xshd index 39d5fa3ec5..f09ff27d93 100644 --- a/src/Libraries/AvalonEdit/ICSharpCode.AvalonEdit/Highlighting/Resources/PHP-Mode.xshd +++ b/src/Libraries/AvalonEdit/ICSharpCode.AvalonEdit/Highlighting/Resources/PHP-Mode.xshd @@ -1,198 +1,158 @@ - - - - - - - - ~!%^*()-+=|\#/{}[]:;"'<> , .? - - - # - - - - /// - - - - //@!/@ - - - - /* - */ - - - - " - " - - - - @@" - " - - - - ' - ' - - - ( - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - ~!@%^*()-+=|\#/{}[]:;"'<> , .? - - - - + + + + + + + + + + + + + + + + + + + \# + + + + // + + + + /\* + \*/ + - - ~!@%^*()-+=|\#/{}[]:;"'<> , .? - - - < - > - - - - - - + + + \b0[xX][0-9a-fA-F]+ # hex number + | + \b0[0-9]+ # octal number + | + ( \b\d+(\.[0-9]+)? #number with optional floating point + | \.[0-9]+ #or just starting with floating point + ) + ([eE][+-]?[0-9]+)? # optional exponent + - - ~!@%^*()-+=|\#/{}[]:;"'<> , .? + + [?,.:;()\[\]{}+\-/%*<>&^!|~@]+ + - - " - " - + + + \b + [\d\w_]+ # an identifier + (?=\s*\() # followed by ( + + + ' + ' + + + + + + + + " + " + + + + + + + + + <<<\"?[\d\w_]+\"?$ + ^[\d\w_]+; + + + + + <<<\'[\d\w_]+\'$ + ^[\d\w_]+; + + + + global + my + var + - - - - - - - + + and + or + new + clone + instanceof + xor + true + false + + + + else + else + switch + case + endif + elseif + + + + do + for + foreach + while + endwhile + exit + + + + break + continue + default + goto + return + + + + require + include + require + include + function + + + + int + integer + real + double + float + string + array + object + + + + class + void + + + + public + private + + - diff --git a/src/Libraries/AvalonEdit/ICSharpCode.AvalonEdit/Rendering/NewLineElementGenerator.cs b/src/Libraries/AvalonEdit/ICSharpCode.AvalonEdit/Rendering/NewLineElementGenerator.cs index dea23c35d7..e81afbb22e 100644 --- a/src/Libraries/AvalonEdit/ICSharpCode.AvalonEdit/Rendering/NewLineElementGenerator.cs +++ b/src/Libraries/AvalonEdit/ICSharpCode.AvalonEdit/Rendering/NewLineElementGenerator.cs @@ -54,7 +54,7 @@ namespace ICSharpCode.AvalonEdit.Rendering } else { return null; } - return new NewLineTextElement(CurrentContext.TextView.cachedElements.GetSimpleLightGrayText(newlineText, CurrentContext)); + return new NewLineTextElement(CurrentContext.TextView.cachedElements.GetTextForNonPrintableCharacter(newlineText, CurrentContext)); } sealed class NewLineTextElement : FormattedTextElement diff --git a/src/Libraries/AvalonEdit/ICSharpCode.AvalonEdit/Rendering/SingleCharacterElementGenerator.cs b/src/Libraries/AvalonEdit/ICSharpCode.AvalonEdit/Rendering/SingleCharacterElementGenerator.cs index da1aacbc45..3d26e7c9b9 100644 --- a/src/Libraries/AvalonEdit/ICSharpCode.AvalonEdit/Rendering/SingleCharacterElementGenerator.cs +++ b/src/Libraries/AvalonEdit/ICSharpCode.AvalonEdit/Rendering/SingleCharacterElementGenerator.cs @@ -88,9 +88,9 @@ namespace ICSharpCode.AvalonEdit.Rendering { char c = CurrentContext.Document.GetCharAt(offset); if (ShowSpaces && c == ' ') { - return new SpaceTextElement(CurrentContext.TextView.cachedElements.GetSimpleLightGrayText("\u00B7", CurrentContext)); + return new SpaceTextElement(CurrentContext.TextView.cachedElements.GetTextForNonPrintableCharacter("\u00B7", CurrentContext)); } else if (ShowTabs && c == '\t') { - return new TabTextElement(CurrentContext.TextView.cachedElements.GetSimpleLightGrayText("\u00BB", CurrentContext)); + return new TabTextElement(CurrentContext.TextView.cachedElements.GetTextForNonPrintableCharacter("\u00BB", CurrentContext)); } else if (ShowBoxForControlCharacters && char.IsControl(c)) { var p = new VisualLineElementTextRunProperties(CurrentContext.GlobalTextRunProperties); p.SetForegroundBrush(Brushes.White); diff --git a/src/Libraries/AvalonEdit/ICSharpCode.AvalonEdit/Rendering/TextView.cs b/src/Libraries/AvalonEdit/ICSharpCode.AvalonEdit/Rendering/TextView.cs index bbd62a2c01..6fbf0b32bf 100644 --- a/src/Libraries/AvalonEdit/ICSharpCode.AvalonEdit/Rendering/TextView.cs +++ b/src/Libraries/AvalonEdit/ICSharpCode.AvalonEdit/Rendering/TextView.cs @@ -110,8 +110,8 @@ namespace ICSharpCode.AvalonEdit.Rendering ClearVisualLines(); if (newValue != null) { TextDocumentWeakEventManager.Changing.AddListener(newValue, this); - heightTree = new HeightTree(newValue, FontSize + 3); formatter = TextFormatterFactory.Create(this); + heightTree = new HeightTree(newValue, DefaultLineHeight); // measuring DefaultLineHeight depends on formatter cachedElements = new TextViewCachedElements(); } InvalidateMeasure(DispatcherPriority.Normal); @@ -367,6 +367,23 @@ namespace ICSharpCode.AvalonEdit.Rendering } #endregion + #region Brushes + /// + /// NonPrintableCharacterBrush dependency property. + /// + public static readonly DependencyProperty NonPrintableCharacterBrushProperty = + DependencyProperty.Register("NonPrintableCharacterBrush", typeof(Brush), typeof(TextView), + new FrameworkPropertyMetadata(Brushes.LightGray)); + + /// + /// Gets/sets the Brush used for displaying non-printable characters. + /// + public Brush NonPrintableCharacterBrush { + get { return (Brush)GetValue(NonPrintableCharacterBrushProperty); } + set { SetValue(NonPrintableCharacterBrushProperty, value); } + } + #endregion + #region Redraw methods / VisualLine invalidation /// /// Causes the text editor to regenerate all visual lines. @@ -1118,12 +1135,12 @@ namespace ICSharpCode.AvalonEdit.Rendering void IScrollInfo.LineUp() { - ((IScrollInfo)this).SetVerticalOffset(scrollOffset.Y - FontSize); + ((IScrollInfo)this).SetVerticalOffset(scrollOffset.Y - DefaultLineHeight); } void IScrollInfo.LineDown() { - ((IScrollInfo)this).SetVerticalOffset(scrollOffset.Y + FontSize); + ((IScrollInfo)this).SetVerticalOffset(scrollOffset.Y + DefaultLineHeight); } void IScrollInfo.LineLeft() @@ -1159,14 +1176,14 @@ namespace ICSharpCode.AvalonEdit.Rendering void IScrollInfo.MouseWheelUp() { ((IScrollInfo)this).SetVerticalOffset( - scrollOffset.Y - (SystemParameters.WheelScrollLines * FontSize)); + scrollOffset.Y - (SystemParameters.WheelScrollLines * DefaultLineHeight)); OnScrollChange(); } void IScrollInfo.MouseWheelDown() { ((IScrollInfo)this).SetVerticalOffset( - scrollOffset.Y + (SystemParameters.WheelScrollLines * FontSize)); + scrollOffset.Y + (SystemParameters.WheelScrollLines * DefaultLineHeight)); OnScrollChange(); } @@ -1184,12 +1201,52 @@ namespace ICSharpCode.AvalonEdit.Rendering OnScrollChange(); } + double wideSpaceWidth; // Width of an 'x'. Used as basis for the tab width, and for scrolling. + double defaultLineHeight; // Height of a line containing 'x'. Used for scrolling. + double WideSpaceWidth { get { - return FontSize / 2; + if (wideSpaceWidth == 0) { + MeasureWideSpaceWidthAndDefaultLineHeight(); + } + return wideSpaceWidth; } } + double DefaultLineHeight { + get { + if (defaultLineHeight == 0) { + MeasureWideSpaceWidthAndDefaultLineHeight(); + } + return defaultLineHeight; + } + } + + void MeasureWideSpaceWidthAndDefaultLineHeight() + { + if (formatter != null) { + var textRunProperties = CreateGlobalTextRunProperties(); + using (var line = formatter.FormatLine( + new SimpleTextSource("x", textRunProperties), + 0, 32000, + new VisualLineTextParagraphProperties { defaultTextRunProperties = textRunProperties }, + null)) + { + wideSpaceWidth = Math.Max(1, line.WidthIncludingTrailingWhitespace); + defaultLineHeight = line.Height; + } + } else { + wideSpaceWidth = FontSize / 2; + defaultLineHeight = FontSize + 3; + } + } + + void InvalidateWideSpaceWidthAndDefaultLineHeight() + { + wideSpaceWidth = 0; + defaultLineHeight = 0; + } + static double ValidateVisualOffset(double offset) { if (double.IsNaN(offset)) @@ -1618,15 +1675,18 @@ namespace ICSharpCode.AvalonEdit.Rendering if (TextFormatterFactory.PropertyChangeAffectsTextFormatter(e.Property)) { RecreateCachedElements(); RecreateTextFormatter(); + InvalidateWideSpaceWidthAndDefaultLineHeight(); } if (e.Property == Control.ForegroundProperty || e.Property == Control.FontFamilyProperty || e.Property == Control.FontSizeProperty || e.Property == Control.FontStretchProperty || e.Property == Control.FontStyleProperty - || e.Property == Control.FontWeightProperty) + || e.Property == Control.FontWeightProperty + || e.Property == TextView.NonPrintableCharacterBrushProperty) { RecreateCachedElements(); + InvalidateWideSpaceWidthAndDefaultLineHeight(); Redraw(); } } diff --git a/src/Libraries/AvalonEdit/ICSharpCode.AvalonEdit/Rendering/TextViewCachedElements.cs b/src/Libraries/AvalonEdit/ICSharpCode.AvalonEdit/Rendering/TextViewCachedElements.cs index c6f21fb312..b76a8a7be8 100644 --- a/src/Libraries/AvalonEdit/ICSharpCode.AvalonEdit/Rendering/TextViewCachedElements.cs +++ b/src/Libraries/AvalonEdit/ICSharpCode.AvalonEdit/Rendering/TextViewCachedElements.cs @@ -12,28 +12,28 @@ namespace ICSharpCode.AvalonEdit.Rendering sealed class TextViewCachedElements : IDisposable { TextFormatter formatter; - Dictionary simpleLightGrayTexts; + Dictionary nonPrintableCharacterTexts; - public TextLine GetSimpleLightGrayText(string text, ITextRunConstructionContext context) + public TextLine GetTextForNonPrintableCharacter(string text, ITextRunConstructionContext context) { - if (simpleLightGrayTexts == null) - simpleLightGrayTexts = new Dictionary(); + if (nonPrintableCharacterTexts == null) + nonPrintableCharacterTexts = new Dictionary(); TextLine textLine; - if (!simpleLightGrayTexts.TryGetValue(text, out textLine)) { + if (!nonPrintableCharacterTexts.TryGetValue(text, out textLine)) { var p = new VisualLineElementTextRunProperties(context.GlobalTextRunProperties); - p.SetForegroundBrush(Brushes.LightGray); + p.SetForegroundBrush(context.TextView.NonPrintableCharacterBrush); if (formatter == null) formatter = TextFormatterFactory.Create(context.TextView); textLine = FormattedTextElement.PrepareText(formatter, text, p); - simpleLightGrayTexts[text] = textLine; + nonPrintableCharacterTexts[text] = textLine; } return textLine; } public void Dispose() { - if (simpleLightGrayTexts != null) { - foreach (TextLine line in simpleLightGrayTexts.Values) + if (nonPrintableCharacterTexts != null) { + foreach (TextLine line in nonPrintableCharacterTexts.Values) line.Dispose(); } if (formatter != null) diff --git a/src/Libraries/AvalonEdit/ICSharpCode.AvalonEdit/TextEditor.cs b/src/Libraries/AvalonEdit/ICSharpCode.AvalonEdit/TextEditor.cs index d3c74ca179..4152385319 100644 --- a/src/Libraries/AvalonEdit/ICSharpCode.AvalonEdit/TextEditor.cs +++ b/src/Libraries/AvalonEdit/ICSharpCode.AvalonEdit/TextEditor.cs @@ -4,6 +4,7 @@ using System; using System.ComponentModel; using System.IO; +using System.Linq; using System.Text; using System.Windows; using System.Windows.Controls; @@ -11,6 +12,7 @@ using System.Windows.Controls.Primitives; using System.Windows.Data; using System.Windows.Input; using System.Windows.Markup; +using System.Windows.Media; using System.Windows.Threading; using ICSharpCode.AvalonEdit.Document; using ICSharpCode.AvalonEdit.Editing; @@ -449,7 +451,7 @@ namespace ICSharpCode.AvalonEdit #region ShowLineNumbers /// - /// IsReadOnly dependency property. + /// ShowLineNumbers dependency property. /// public static readonly DependencyProperty ShowLineNumbersProperty = DependencyProperty.Register("ShowLineNumbers", typeof(bool), typeof(TextEditor), @@ -468,8 +470,13 @@ namespace ICSharpCode.AvalonEdit TextEditor editor = (TextEditor)d; var leftMargins = editor.TextArea.LeftMargins; if ((bool)e.NewValue) { - leftMargins.Insert(0, new LineNumberMargin()); - leftMargins.Insert(1, DottedLineMargin.Create()); + var lineNumbers = new LineNumberMargin(); + leftMargins.Insert(0, lineNumbers); + leftMargins.Insert(1, DottedLineMargin.Create(editor)); + lineNumbers.SetBinding(Control.ForegroundProperty, + new Binding("LineNumbersForeground") { + Source = editor + }); } else { for (int i = 0; i < leftMargins.Count; i++) { if (leftMargins[i] is LineNumberMargin) { @@ -484,6 +491,33 @@ namespace ICSharpCode.AvalonEdit } #endregion + #region LineNumbersForeground + /// + /// LineNumbersForeground dependency property. + /// + public static readonly DependencyProperty LineNumbersForegroundProperty = + DependencyProperty.Register("LineNumbersForeground", typeof(Brush), typeof(TextEditor), + new FrameworkPropertyMetadata(Brushes.Gray, OnLineNumbersForegroundChanged)); + + /// + /// Gets/sets the Brush used for displaying the foreground color of line numbers. + /// + public Brush LineNumbersForeground { + get { return (Brush)GetValue(LineNumbersForegroundProperty); } + set { SetValue(LineNumbersForegroundProperty, value); } + } + + static void OnLineNumbersForegroundChanged(DependencyObject d, DependencyPropertyChangedEventArgs e) + { + TextEditor editor = (TextEditor)d; + var lineNumberMargin = editor.TextArea.LeftMargins.FirstOrDefault(margin => margin is LineNumberMargin) as LineNumberMargin;; + + if (lineNumberMargin != null) { + lineNumberMargin.SetValue(Control.ForegroundProperty, e.NewValue); + } + } + #endregion + #region TextBoxBase-like methods /// /// Appends text to the end of the document. diff --git a/src/Libraries/AvalonEdit/ICSharpCode.AvalonEdit/Utils/Deque.cs b/src/Libraries/AvalonEdit/ICSharpCode.AvalonEdit/Utils/Deque.cs index 2bb3c31424..373b5f5f70 100644 --- a/src/Libraries/AvalonEdit/ICSharpCode.AvalonEdit/Utils/Deque.cs +++ b/src/Libraries/AvalonEdit/ICSharpCode.AvalonEdit/Utils/Deque.cs @@ -12,7 +12,7 @@ namespace ICSharpCode.AvalonEdit.Utils /// [System.Diagnostics.CodeAnalysis.SuppressMessage("Microsoft.Naming", "CA1710:IdentifiersShouldHaveCorrectSuffix")] [Serializable] - public class Deque : ICollection + public sealed class Deque : ICollection { T[] arr = Empty.Array; int size, head, tail; diff --git a/src/Libraries/AvalonEdit/ICSharpCode.AvalonEdit/Xml/AXmlParser.cs b/src/Libraries/AvalonEdit/ICSharpCode.AvalonEdit/Xml/AXmlParser.cs index eb282e9628..a068bb8b77 100644 --- a/src/Libraries/AvalonEdit/ICSharpCode.AvalonEdit/Xml/AXmlParser.cs +++ b/src/Libraries/AvalonEdit/ICSharpCode.AvalonEdit/Xml/AXmlParser.cs @@ -97,15 +97,8 @@ namespace ICSharpCode.AvalonEdit.Xml /// Create new parser public AXmlParser() { - this.UnknownEntityReferenceIsError = true; - this.TrackedSegments = new TrackedSegmentCollection(); this.Lock = new ReaderWriterLockSlim(LockRecursionPolicy.SupportsRecursion); - - this.userDocument = new AXmlDocument() { Parser = this }; - this.userDocument.Document = this.userDocument; - // Track the document - this.TrackedSegments.AddParsedObject(this.userDocument, null); - this.userDocument.IsCached = false; + ClearInternal(); } /// Throws exception if condition is false @@ -181,5 +174,28 @@ namespace ICSharpCode.AvalonEdit.Xml return userDocument; } } + + /// + /// Clears the parser data. + /// + /// No write lock is held by the current thread. + public void Clear() + { + if (!Lock.IsWriteLockHeld) + throw new InvalidOperationException("Write lock needed!"); + + ClearInternal(); + } + + void ClearInternal() + { + this.UnknownEntityReferenceIsError = true; + this.TrackedSegments = new TrackedSegmentCollection(); + this.userDocument = new AXmlDocument() { Parser = this }; + this.userDocument.Document = this.userDocument; + // Track the document + this.TrackedSegments.AddParsedObject(this.userDocument, null); + this.userDocument.IsCached = false; + } } } diff --git a/src/Libraries/AvalonEdit/ICSharpCode.AvalonEdit/themes/generic.xaml b/src/Libraries/AvalonEdit/ICSharpCode.AvalonEdit/themes/generic.xaml index a2d821d61c..ad76a3eea0 100644 --- a/src/Libraries/AvalonEdit/ICSharpCode.AvalonEdit/themes/generic.xaml +++ b/src/Libraries/AvalonEdit/ICSharpCode.AvalonEdit/themes/generic.xaml @@ -9,7 +9,6 @@ diff --git a/src/Libraries/NRefactory/Project/Src/PrettyPrinter/CSharp/CSharpOutputVisitor.cs b/src/Libraries/NRefactory/Project/Src/PrettyPrinter/CSharp/CSharpOutputVisitor.cs index f4d8d8b7f9..ac9c05394a 100644 --- a/src/Libraries/NRefactory/Project/Src/PrettyPrinter/CSharp/CSharpOutputVisitor.cs +++ b/src/Libraries/NRefactory/Project/Src/PrettyPrinter/CSharp/CSharpOutputVisitor.cs @@ -1956,12 +1956,15 @@ namespace ICSharpCode.NRefactory.PrettyPrinter else TrackVisit(forNextStatement.LoopVariableExpression, data); outputFormatter.Space(); - PrimitiveExpression pe = forNextStatement.Step as PrimitiveExpression; + Expression stepExpr = forNextStatement.Step; + while (stepExpr is ParenthesizedExpression) + stepExpr = ((ParenthesizedExpression)stepExpr).Expression; + PrimitiveExpression pe = stepExpr as PrimitiveExpression; if ((pe == null || !(pe.Value is int) || ((int)pe.Value) >= 0) - && !(forNextStatement.Step is UnaryOperatorExpression)) + && !(stepExpr is UnaryOperatorExpression)) outputFormatter.PrintToken(Tokens.LessEqual); else { - if (forNextStatement.Step is UnaryOperatorExpression && ((UnaryOperatorExpression)forNextStatement.Step).Op == UnaryOperatorType.Plus) + if (stepExpr is UnaryOperatorExpression && ((UnaryOperatorExpression)stepExpr).Op == UnaryOperatorType.Plus) outputFormatter.PrintToken(Tokens.LessEqual); else outputFormatter.PrintToken(Tokens.GreaterEqual); diff --git a/src/Main/Base/Project/Src/Bookmarks/Commands/MenuCommands.cs b/src/Main/Base/Project/Src/Bookmarks/Commands/MenuCommands.cs index 5569f0d7bd..963a65cd59 100644 --- a/src/Main/Base/Project/Src/Bookmarks/Commands/MenuCommands.cs +++ b/src/Main/Base/Project/Src/Bookmarks/Commands/MenuCommands.cs @@ -41,12 +41,11 @@ namespace ICSharpCode.SharpDevelop.Bookmarks protected override void Run(ITextEditor editor, IBookmarkMargin bookmarkMargin) { BookmarkManager.ToggleBookmark(editor, editor.Caret.Line, - b => b.CanToggle, + b => b.CanToggle && b.GetType() == typeof(SDBookmark), location => new SDBookmark(editor.FileName, location)); } } - - public class PrevBookmark : BookmarkMenuCommand + public class PrevBookmark : BookmarkMenuCommand { protected override void Run(ITextEditor editor, IBookmarkMargin bookmarkMargin) { diff --git a/src/Main/Base/Project/Src/Editor/Search/ProvidedDocumentInformation.cs b/src/Main/Base/Project/Src/Editor/Search/ProvidedDocumentInformation.cs index 0325d8133e..f33b2829c6 100644 --- a/src/Main/Base/Project/Src/Editor/Search/ProvidedDocumentInformation.cs +++ b/src/Main/Base/Project/Src/Editor/Search/ProvidedDocumentInformation.cs @@ -15,6 +15,7 @@ namespace ICSharpCode.SharpDevelop.Editor.Search ITextBuffer textBuffer; FileName fileName; int currentOffset; + bool documentCreatedFromTextBuffer; public FileName FileName { get { @@ -35,8 +36,8 @@ namespace ICSharpCode.SharpDevelop.Editor.Search } } - public bool IsDocumentCreated { - get { return document != null; } + public bool IsDocumentCreatedFromTextBuffer { + get { return documentCreatedFromTextBuffer; } } public int CurrentOffset { @@ -109,6 +110,7 @@ namespace ICSharpCode.SharpDevelop.Editor.Search this.textBuffer = textBuffer; this.fileName = FileName.Create(fileName); this.endOffset = this.currentOffset = currentOffset; + documentCreatedFromTextBuffer = true; } } } diff --git a/src/Main/Base/Project/Src/Gui/Components/ColorPicker.xaml.cs b/src/Main/Base/Project/Src/Gui/Components/ColorPicker.xaml.cs index 3a3fcdfc0b..93740e689d 100644 --- a/src/Main/Base/Project/Src/Gui/Components/ColorPicker.xaml.cs +++ b/src/Main/Base/Project/Src/Gui/Components/ColorPicker.xaml.cs @@ -2,15 +2,14 @@ // This code is distributed under the GNU LGPL (for details please see \doc\license.txt) using System; -using System.Collections.Generic; -using System.Text; using System.Windows; using System.Windows.Controls; +using System.Windows.Controls.Primitives; using System.Windows.Data; -using System.Windows.Documents; -using System.Windows.Input; using System.Windows.Media; +using Widgets = ICSharpCode.SharpDevelop.Widgets; + namespace ICSharpCode.SharpDevelop.Gui { /// @@ -60,14 +59,22 @@ namespace ICSharpCode.SharpDevelop.Gui void ButtonClick(object sender, RoutedEventArgs e) { - e.Handled = true; - using (SharpDevelopColorDialog dlg = new SharpDevelopColorDialog()) { - dlg.WpfColor = this.Value; - if (dlg.ShowWpfDialog() == true) { - // use SetCurrentValue instead of SetValue so that two-way data binding can be used - SetCurrentValue(ValueProperty, dlg.WpfColor); + var control = new Widgets.ColorPicker(); + Popup popup = new Popup() { + Child = control, + Placement = PlacementMode.Bottom, + PlacementTarget = this, + IsOpen = true, + StaysOpen = false + }; + + control.SetBinding( + Widgets.ColorPicker.ColorProperty, + new Binding("Value") { + Source = this, + Mode = BindingMode.TwoWay } - } + ); } } } diff --git a/src/Main/Base/Project/Src/Gui/Dialogs/NewFileDialog.cs b/src/Main/Base/Project/Src/Gui/Dialogs/NewFileDialog.cs index 43d6e0b8b6..534267bfa4 100644 --- a/src/Main/Base/Project/Src/Gui/Dialogs/NewFileDialog.cs +++ b/src/Main/Base/Project/Src/Gui/Dialogs/NewFileDialog.cs @@ -9,8 +9,8 @@ using System.IO; using System.Linq; using System.Text; using System.Windows.Forms; - using ICSharpCode.Core; +using ICSharpCode.Core.Services; using ICSharpCode.SharpDevelop.Editor; using ICSharpCode.SharpDevelop.Gui.XmlForms; using ICSharpCode.SharpDevelop.Internal.Templates; @@ -505,14 +505,20 @@ namespace ICSharpCode.SharpDevelop.Gui } } ScriptRunner scriptRunner = new ScriptRunner(); - - foreach (FileDescriptionTemplate newfile in item.Template.FileDescriptionTemplates) { - if (!String.IsNullOrEmpty(newfile.BinaryFileName)) { - SaveFile(newfile, null, newfile.BinaryFileName); - } else { - SaveFile(newfile, scriptRunner.CompileScript(item.Template, newfile), null); - } + foreach (FileDescriptionTemplate newFile in item.Template.FileDescriptionTemplates) { + FileOperationResult result = FileUtility.ObservedSave( + () => { + if (!String.IsNullOrEmpty(newFile.BinaryFileName)) { + SaveFile(newFile, null, newFile.BinaryFileName); + } else { + SaveFile(newFile, scriptRunner.CompileScript(item.Template, newFile), null); + } + }, StringParser.Parse(newFile.Name) + ); + if (result != FileOperationResult.OK) + return; } + DialogResult = DialogResult.OK; // raise FileCreated event for the new files. diff --git a/src/Main/Base/Project/Src/Gui/IProgressMonitor.cs b/src/Main/Base/Project/Src/Gui/IProgressMonitor.cs index 878467001c..5a64f85bb5 100644 --- a/src/Main/Base/Project/Src/Gui/IProgressMonitor.cs +++ b/src/Main/Base/Project/Src/Gui/IProgressMonitor.cs @@ -120,15 +120,13 @@ namespace ICSharpCode.SharpDevelop.Gui public OperationStatus Status { get; set; } - public CancellationToken CancellationToken { - get { return CancellationToken.None; } - } + public CancellationToken CancellationToken { get; set; } public double Progress { get; set; } public IProgressMonitor CreateSubTask(double workAmount) { - return new DummyProgressMonitor(); + return new DummyProgressMonitor() { CancellationToken = this.CancellationToken }; } public void Dispose() diff --git a/src/Main/Base/Project/Src/Gui/Pads/TaskList/TaskView.cs b/src/Main/Base/Project/Src/Gui/Pads/TaskList/TaskView.cs index 06986a6249..f0e8d07846 100644 --- a/src/Main/Base/Project/Src/Gui/Pads/TaskList/TaskView.cs +++ b/src/Main/Base/Project/Src/Gui/Pads/TaskList/TaskView.cs @@ -106,6 +106,7 @@ namespace ICSharpCode.SharpDevelop.Gui this.Columns.Add(file); this.Columns.Add(path); + this.HideSelection = false; this.FullRowSelect = true; this.AutoArrange = true; this.Alignment = ListViewAlignment.Left; diff --git a/src/Main/Base/Project/Src/Services/File/FileService.cs b/src/Main/Base/Project/Src/Services/File/FileService.cs index 07b41e60d1..f3f115975f 100644 --- a/src/Main/Base/Project/Src/Services/File/FileService.cs +++ b/src/Main/Base/Project/Src/Services/File/FileService.cs @@ -412,8 +412,7 @@ namespace ICSharpCode.SharpDevelop Directory.Delete(fileName, true); } } catch (Exception e) { - MessageService.ShowException(e, "Can't remove directory " + fileName); -// return; + MessageService.ShowHandledException(e, "Can't remove directory " + fileName); } } else { try { @@ -424,8 +423,7 @@ namespace ICSharpCode.SharpDevelop File.Delete(fileName); } } catch (Exception e) { - MessageService.ShowException(e, "Can't remove file " + fileName); -// return; + MessageService.ShowHandledException(e, "Can't remove file " + fileName); } } } @@ -464,9 +462,9 @@ namespace ICSharpCode.SharpDevelop } } catch (Exception e) { if (isDirectory) { - MessageService.ShowException(e, "Can't rename directory " + oldName); + MessageService.ShowHandledException(e, "Can't rename directory " + oldName); } else { - MessageService.ShowException(e, "Can't rename file " + oldName); + MessageService.ShowHandledException(e, "Can't rename file " + oldName); } return false; } @@ -508,9 +506,9 @@ namespace ICSharpCode.SharpDevelop } } catch (Exception e) { if (isDirectory) { - MessageService.ShowException(e, "Can't copy directory " + oldName); + MessageService.ShowHandledException(e, "Can't copy directory " + oldName); } else { - MessageService.ShowException(e, "Can't copy file " + oldName); + MessageService.ShowHandledException(e, "Can't copy file " + oldName); } return false; } diff --git a/src/Main/Base/Project/Src/Services/RefactoringService/RefactoringService.cs b/src/Main/Base/Project/Src/Services/RefactoringService/RefactoringService.cs index 853be79220..7924d13692 100644 --- a/src/Main/Base/Project/Src/Services/RefactoringService/RefactoringService.cs +++ b/src/Main/Base/Project/Src/Services/RefactoringService/RefactoringService.cs @@ -6,6 +6,7 @@ using System.Collections.Generic; using System.Diagnostics; using System.Drawing; using System.Linq; +using System.Threading; using ICSharpCode.Core; using ICSharpCode.SharpDevelop.Dom; @@ -228,6 +229,9 @@ namespace ICSharpCode.SharpDevelop.Refactoring if (progressMonitor != null) progressMonitor.ShowingDialog = false; return null; } + + CancellationToken ct = progressMonitor != null ? progressMonitor.CancellationToken : CancellationToken.None; + List files; if (!string.IsNullOrEmpty(fileName)) { // search just in given file @@ -249,7 +253,7 @@ namespace ICSharpCode.SharpDevelop.Refactoring if (progressMonitor != null) { progressMonitor.Progress += 1.0 / files.Count; - if (progressMonitor.CancellationToken.IsCancellationRequested) + if (ct.IsCancellationRequested) return null; } // Don't read files we don't have a parser for. @@ -257,7 +261,14 @@ namespace ICSharpCode.SharpDevelop.Refactoring if (ParserService.GetParser(itemFileName) != null) { ITextBuffer content = finder.Create(itemFileName); if (content != null) { - AddReferences(references, ownerClass, member, itemFileName, content.Text); + try { + AddReferences(references, ownerClass, member, itemFileName, content.Text, ct); + } catch (OperationCanceledException ex) { + if (ex.CancellationToken == ct) + return null; + else + throw; + } } } } @@ -270,7 +281,8 @@ namespace ICSharpCode.SharpDevelop.Refactoring /// static void AddReferences(List list, IClass parentClass, IMember member, - string fileName, string fileContent) + string fileName, string fileContent, + CancellationToken cancellationToken) { TextFinder textFinder; // the class used to find the position to resolve if (member == null) { @@ -292,6 +304,7 @@ namespace ICSharpCode.SharpDevelop.Refactoring TextFinderMatch match = new TextFinderMatch(-1, 0); while (true) { + cancellationToken.ThrowIfCancellationRequested(); match = textFinder.Find(fileContentForFinder, match.Position + 1); if (match.Position < 0) break; @@ -307,6 +320,7 @@ namespace ICSharpCode.SharpDevelop.Refactoring if (expr.Expression != null) { Point position = GetPosition(fileContent, match.ResolvePosition); repeatResolve: + cancellationToken.ThrowIfCancellationRequested(); // TODO: Optimize by re-using the same resolver if multiple expressions were // found in this file (the resolver should parse all methods at once) ResolveResult rr = ParserService.Resolve(expr, position.Y, position.X, fileName, fileContent); diff --git a/src/Main/Core/Project/Src/Services/MessageService/MessageService.cs b/src/Main/Core/Project/Src/Services/MessageService/MessageService.cs index ca41f38b4f..20777b1058 100644 --- a/src/Main/Core/Project/Src/Services/MessageService/MessageService.cs +++ b/src/Main/Core/Project/Src/Services/MessageService/MessageService.cs @@ -52,6 +52,33 @@ namespace ICSharpCode.Core ServiceManager.Instance.MessageService.ShowException(ex, message); } + /// + /// Shows an exception. + /// + public static void ShowHandledException(Exception ex) + { + ShowHandledException(ex, null); + } + + /// + /// Shows an exception. + /// + public static void ShowHandledException(Exception ex, string message) + { + LoggingService.Error(message, ex); + LoggingService.Warn("Stack trace of last exception log:\n" + Environment.StackTrace); + message = GetMessage(message, ex); + ServiceManager.Instance.MessageService.ShowError(message); + } + + static string GetMessage(string message, Exception ex) + { + if (message == null) { + return ex.Message; + } + return message + "\r\n\r\n" + ex.Message; + } + /// /// Shows a warning message. /// diff --git a/src/AddIns/DisplayBindings/WpfDesign/WpfDesign.Designer/Project/PropertyGrid/Editors/BrushEditor/ColorHelper.cs b/src/Main/ICSharpCode.SharpDevelop.Widgets/Project/ColorHelper.cs similarity index 96% rename from src/AddIns/DisplayBindings/WpfDesign/WpfDesign.Designer/Project/PropertyGrid/Editors/BrushEditor/ColorHelper.cs rename to src/Main/ICSharpCode.SharpDevelop.Widgets/Project/ColorHelper.cs index 3196c7e584..6df1e66c4d 100644 --- a/src/AddIns/DisplayBindings/WpfDesign/WpfDesign.Designer/Project/PropertyGrid/Editors/BrushEditor/ColorHelper.cs +++ b/src/Main/ICSharpCode.SharpDevelop.Widgets/Project/ColorHelper.cs @@ -7,7 +7,7 @@ using System.Linq; using System.Text; using System.Windows.Media; -namespace ICSharpCode.WpfDesign.Designer.PropertyGrid.Editors.BrushEditor +namespace ICSharpCode.SharpDevelop.Widgets { public static class ColorHelper { diff --git a/src/AddIns/DisplayBindings/WpfDesign/WpfDesign.Designer/Project/PropertyGrid/Editors/BrushEditor/ColorPicker.xaml b/src/Main/ICSharpCode.SharpDevelop.Widgets/Project/ColorPicker.xaml similarity index 90% rename from src/AddIns/DisplayBindings/WpfDesign/WpfDesign.Designer/Project/PropertyGrid/Editors/BrushEditor/ColorPicker.xaml rename to src/Main/ICSharpCode.SharpDevelop.Widgets/Project/ColorPicker.xaml index 730e55bb3a..efa3758076 100644 --- a/src/AddIns/DisplayBindings/WpfDesign/WpfDesign.Designer/Project/PropertyGrid/Editors/BrushEditor/ColorPicker.xaml +++ b/src/Main/ICSharpCode.SharpDevelop.Widgets/Project/ColorPicker.xaml @@ -1,9 +1,7 @@ - @@ -55,7 +53,7 @@ - @@ -143,7 +141,7 @@ - - + - - - - + + diff --git a/src/AddIns/DisplayBindings/WpfDesign/WpfDesign.Designer/Project/PropertyGrid/Editors/BrushEditor/ColorPicker.xaml.cs b/src/Main/ICSharpCode.SharpDevelop.Widgets/Project/ColorPicker.xaml.cs similarity index 98% rename from src/AddIns/DisplayBindings/WpfDesign/WpfDesign.Designer/Project/PropertyGrid/Editors/BrushEditor/ColorPicker.xaml.cs rename to src/Main/ICSharpCode.SharpDevelop.Widgets/Project/ColorPicker.xaml.cs index 20027bc148..ba7d4a2be2 100644 --- a/src/AddIns/DisplayBindings/WpfDesign/WpfDesign.Designer/Project/PropertyGrid/Editors/BrushEditor/ColorPicker.xaml.cs +++ b/src/Main/ICSharpCode.SharpDevelop.Widgets/Project/ColorPicker.xaml.cs @@ -16,7 +16,7 @@ using System.Windows.Navigation; using System.Windows.Shapes; using System.ComponentModel; -namespace ICSharpCode.WpfDesign.Designer.PropertyGrid.Editors.BrushEditor +namespace ICSharpCode.SharpDevelop.Widgets { public partial class ColorPicker { diff --git a/src/Main/ICSharpCode.SharpDevelop.Widgets/Project/ICSharpCode.SharpDevelop.Widgets.csproj b/src/Main/ICSharpCode.SharpDevelop.Widgets/Project/ICSharpCode.SharpDevelop.Widgets.csproj index 70f8c2d0af..b8fb0e7900 100644 --- a/src/Main/ICSharpCode.SharpDevelop.Widgets/Project/ICSharpCode.SharpDevelop.Widgets.csproj +++ b/src/Main/ICSharpCode.SharpDevelop.Widgets/Project/ICSharpCode.SharpDevelop.Widgets.csproj @@ -63,6 +63,10 @@ Configuration\GlobalAssemblyInfo.cs + + + ColorPicker.xaml + @@ -76,6 +80,7 @@ NumericUpDown.xaml + @@ -99,6 +104,10 @@ + + MSBuild:Compile + Designer + diff --git a/src/AddIns/DisplayBindings/WpfDesign/WpfDesign.Designer/Project/PropertyGrid/Editors/BrushEditor/Picker.cs b/src/Main/ICSharpCode.SharpDevelop.Widgets/Project/Picker.cs similarity index 98% rename from src/AddIns/DisplayBindings/WpfDesign/WpfDesign.Designer/Project/PropertyGrid/Editors/BrushEditor/Picker.cs rename to src/Main/ICSharpCode.SharpDevelop.Widgets/Project/Picker.cs index 86431dda27..187e74f948 100644 --- a/src/AddIns/DisplayBindings/WpfDesign/WpfDesign.Designer/Project/PropertyGrid/Editors/BrushEditor/Picker.cs +++ b/src/Main/ICSharpCode.SharpDevelop.Widgets/Project/Picker.cs @@ -12,7 +12,7 @@ using System.Windows.Controls; using System.Windows.Media; using System.Windows.Data; -namespace ICSharpCode.WpfDesign.Designer.PropertyGrid.Editors.BrushEditor +namespace ICSharpCode.SharpDevelop.Widgets { public class Picker : Grid {