diff --git a/src/Main/Base/Project/Src/Services/RefactoringService/RefactoringService.cs b/src/Main/Base/Project/Src/Services/RefactoringService/RefactoringService.cs index 13c001cedd..53b9ca3f2a 100644 --- a/src/Main/Base/Project/Src/Services/RefactoringService/RefactoringService.cs +++ b/src/Main/Base/Project/Src/Services/RefactoringService/RefactoringService.cs @@ -229,32 +229,17 @@ namespace ICSharpCode.SharpDevelop.Refactoring // found in this file (the resolver should parse all methods at once) ResolveResult rr = ParserService.Resolve(expr, position.Y, position.X, fileName, fileContent); MemberResolveResult mrr = rr as MemberResolveResult; - if (isLocal) { - // find reference to local variable - if (IsReferenceToLocalVariable(rr, member)) { - list.Add(new Reference(fileName, match.Position, match.Length, expr.Expression, rr)); - } else if (FixIndexerExpression(expressionFinder, ref expr, mrr)) { - goto repeatResolve; - } - } else if (member != null) { + if (member != null) { // find reference to member - if (IsReferenceToMember(member, rr)) { + if (rr != null && rr.IsReferenceTo(member)) { list.Add(new Reference(fileName, match.Position, match.Length, expr.Expression, rr)); } else if (FixIndexerExpression(expressionFinder, ref expr, mrr)) { goto repeatResolve; } } else { // find reference to class - if (mrr != null) { - if (mrr.ResolvedMember is IMethod && ((IMethod)mrr.ResolvedMember).IsConstructor) { - if (mrr.ResolvedMember.DeclaringType.FullyQualifiedName == parentClass.FullyQualifiedName) { - list.Add(new Reference(fileName, match.Position, match.Length, expr.Expression, rr)); - } - } - } else { - if (rr is TypeResolveResult && rr.ResolvedType.FullyQualifiedName == parentClass.FullyQualifiedName) { - list.Add(new Reference(fileName, match.Position, match.Length, expr.Expression, rr)); - } + if (rr != null && rr.IsReferenceTo(parentClass)) { + list.Add(new Reference(fileName, match.Position, match.Length, expr.Expression, rr)); } } } @@ -404,33 +389,5 @@ namespace ICSharpCode.SharpDevelop.Refactoring } } #endregion - - #region IsReferenceTo... - public static bool IsReferenceToLocalVariable(ResolveResult rr, IMember variable) - { - LocalResolveResult local = rr as LocalResolveResult; - if (local == null) { - return false; - } else { - return local.VariableDefinitionRegion.BeginLine == variable.Region.BeginLine - && local.VariableDefinitionRegion.BeginColumn == variable.Region.BeginColumn; - } - } - - /// - /// Gets if is a reference to . - /// - public static bool IsReferenceToMember(IMember member, ResolveResult rr) - { - MemberResolveResult mrr = rr as MemberResolveResult; - if (mrr != null) { - return MemberLookupHelper.IsSimilarMember(mrr.ResolvedMember, member); - } else if (rr is MethodGroupResolveResult) { - return MemberLookupHelper.IsSimilarMember((rr as MethodGroupResolveResult).GetMethodIfSingleOverload(), member); - } else { - return false; - } - } - #endregion } } diff --git a/src/Main/Base/Test/GenericResolverTests.cs b/src/Main/Base/Test/GenericResolverTests.cs index da167c7db4..6dd13e6636 100644 --- a/src/Main/Base/Test/GenericResolverTests.cs +++ b/src/Main/Base/Test/GenericResolverTests.cs @@ -356,7 +356,7 @@ class TestClass { // ensure that the reference pointing to the specialized method is seen as a reference // to the generic method. - Assert.IsTrue(Refactoring.RefactoringService.IsReferenceToMember(genericMethod, mrr)); + Assert.IsTrue(mrr.IsReferenceTo(genericMethod)); } [Test] @@ -386,15 +386,15 @@ class TestClass { Assert.AreSame(nonGenericMethod, mrr.ResolvedMember); - Assert.IsTrue(Refactoring.RefactoringService.IsReferenceToMember(nonGenericMethod, mrr)); - Assert.IsFalse(Refactoring.RefactoringService.IsReferenceToMember(genericMethod, mrr)); + Assert.IsTrue(mrr.IsReferenceTo(nonGenericMethod)); + Assert.IsFalse(mrr.IsReferenceTo(genericMethod)); mrr = Resolve(program, "GetSomething()", 4); Assert.AreEqual("System.Int32", mrr.ResolvedType.FullyQualifiedName); Assert.AreEqual("System.Int32", mrr.ResolvedMember.ReturnType.FullyQualifiedName); - Assert.IsTrue(Refactoring.RefactoringService.IsReferenceToMember(genericMethod, mrr)); - Assert.IsFalse(Refactoring.RefactoringService.IsReferenceToMember(nonGenericMethod, mrr)); + Assert.IsTrue(mrr.IsReferenceTo(genericMethod)); + Assert.IsFalse(mrr.IsReferenceTo(nonGenericMethod)); } [Test] diff --git a/src/Main/Base/Test/NRefactoryResolverTests.cs b/src/Main/Base/Test/NRefactoryResolverTests.cs index 1273669fe4..b58166fbb3 100644 --- a/src/Main/Base/Test/NRefactoryResolverTests.cs +++ b/src/Main/Base/Test/NRefactoryResolverTests.cs @@ -823,8 +823,8 @@ class C : B { // ensure that the reference pointing to the B ctor is not seen as a reference // to the A ctor. - Assert.IsTrue(Refactoring.RefactoringService.IsReferenceToMember(bCtor, mrr)); - Assert.IsFalse(Refactoring.RefactoringService.IsReferenceToMember(aCtor, mrr)); + Assert.IsTrue(mrr.IsReferenceTo(bCtor)); + Assert.IsFalse(mrr.IsReferenceTo(aCtor)); } [Test] @@ -1923,7 +1923,8 @@ public class MyCollectionType : System.Collections.IEnumerable var dcrr = Resolve(program, "BaseClass.Test()", 4); Assert.AreEqual("SomeDelegate.Invoke", dcrr.DelegateInvokeMethod.FullyQualifiedName); var mrr = dcrr.Target as MemberResolveResult; - Assert.AreEqual("BaseClass.Test", mrr.ResolvedMember.FullyQualifiedName); + IMember baseClassTest = mrr.ResolvedMember; + Assert.AreEqual("BaseClass.Test", baseClassTest.FullyQualifiedName); mrr = Resolve(program, "Test", 4); Assert.AreEqual("DerivedClass.Test", mrr.ResolvedMember.FullyQualifiedName); @@ -1935,6 +1936,7 @@ public class MyCollectionType : System.Collections.IEnumerable dcrr = Resolve(program, "DerivedClass.Test()", 4); mrr = (MemberResolveResult)dcrr.Target; Assert.AreEqual("BaseClass.Test", mrr.ResolvedMember.FullyQualifiedName); + Assert.IsTrue(dcrr.IsReferenceTo(baseClassTest)); } [Test] diff --git a/src/Main/ICSharpCode.SharpDevelop.Dom/Project/Src/LanguageProperties.cs b/src/Main/ICSharpCode.SharpDevelop.Dom/Project/Src/LanguageProperties.cs index d0654a9850..580a374d15 100644 --- a/src/Main/ICSharpCode.SharpDevelop.Dom/Project/Src/LanguageProperties.cs +++ b/src/Main/ICSharpCode.SharpDevelop.Dom/Project/Src/LanguageProperties.cs @@ -21,7 +21,7 @@ namespace ICSharpCode.SharpDevelop.Dom public readonly static LanguageProperties None = new LanguageProperties(StringComparer.InvariantCulture); /// - /// C# 2.0 language properties. + /// C# 3.0 language properties. /// public readonly static LanguageProperties CSharp = new CSharpProperties(); diff --git a/src/Main/ICSharpCode.SharpDevelop.Dom/Project/Src/ResolveResult.cs b/src/Main/ICSharpCode.SharpDevelop.Dom/Project/Src/ResolveResult.cs index fa92cd7ddd..0bc4875ec7 100644 --- a/src/Main/ICSharpCode.SharpDevelop.Dom/Project/Src/ResolveResult.cs +++ b/src/Main/ICSharpCode.SharpDevelop.Dom/Project/Src/ResolveResult.cs @@ -145,6 +145,14 @@ namespace ICSharpCode.SharpDevelop.Dom // this is only possible on some subclasses of ResolveResult return FilePosition.Empty; } + + /// + /// Gets if this ResolveResult represents a reference to the specified entity. + /// + public virtual bool IsReferenceTo(IEntity entity) + { + return false; + } } #endregion @@ -220,6 +228,11 @@ namespace ICSharpCode.SharpDevelop.Dom { return new MixedResolveResult(primaryResult.Clone(), secondaryResult.Clone()); } + + public override bool IsReferenceTo(IEntity entity) + { + return primaryResult.IsReferenceTo(entity) || secondaryResult.IsReferenceTo(entity); + } } #endregion @@ -304,6 +317,16 @@ namespace ICSharpCode.SharpDevelop.Dom return new FilePosition(cu.FileName); } } + + public override bool IsReferenceTo(IEntity entity) + { + IField f = entity as IField; + if (f != null && (f.IsLocalVariable || f.IsParameter)) { + return field.Region.BeginLine == f.Region.BeginLine + && field.Region.BeginColumn == f.Region.BeginColumn; + } + return base.IsReferenceTo(entity); + } } #endregion @@ -450,6 +473,14 @@ namespace ICSharpCode.SharpDevelop.Dom else return new FilePosition(cu.FileName); } + + public override bool IsReferenceTo(IEntity entity) + { + IClass c = entity as IClass; + return c != null + && resolvedClass.FullyQualifiedName == c.FullyQualifiedName + && resolvedClass.TypeParameters.Count == c.TypeParameters.Count; + } } #endregion @@ -530,6 +561,19 @@ namespace ICSharpCode.SharpDevelop.Dom else return new FilePosition(cu.FileName); } + + public override bool IsReferenceTo(IEntity entity) + { + IClass c = entity as IClass; + if (c != null) { + IMethod m = resolvedMember as IMethod; + return m != null && m.IsConstructor + && m.DeclaringType.FullyQualifiedName == c.FullyQualifiedName + && m.DeclaringType.TypeParameters.Count == c.TypeParameters.Count; + } else { + return MemberLookupHelper.IsSimilarMember(resolvedMember, entity as IMember); + } + } } #endregion @@ -733,6 +777,11 @@ namespace ICSharpCode.SharpDevelop.Dom else return base.GetDefinitionPosition(); } + + public override bool IsReferenceTo(IEntity entity) + { + return MemberLookupHelper.IsSimilarMember(GetMethodIfSingleOverload(), entity as IMember); + } } #endregion @@ -848,6 +897,16 @@ namespace ICSharpCode.SharpDevelop.Dom { return new DelegateCallResolveResult(targetRR, delegateInvokeMethod); } + + public override FilePosition GetDefinitionPosition() + { + return targetRR.GetDefinitionPosition(); + } + + public override bool IsReferenceTo(ICSharpCode.SharpDevelop.Dom.IEntity entity) + { + return targetRR.IsReferenceTo(entity); + } } #endregion