When producing code completion results for the Objective-C property

implementation 

  @synthesize <property> = 

also produce a completion for a to-be-synthesized ivar named
_<property>.

llvm-svn: 129697
This commit is contained in:
Douglas Gregor
2011-04-18 14:13:53 +00:00
parent 7170f064c0
commit 331faa0f73
2 changed files with 46 additions and 7 deletions

View File

@@ -5372,14 +5372,51 @@ void Sema::CodeCompleteObjCPropertySynthesizeIvar(Scope *S,
// Add all of the instance variables in this class and its superclasses.
Results.EnterNewScope();
bool SawSimilarlyNamedIvar = false;
std::string NameWithPrefix;
NameWithPrefix += '_';
NameWithPrefix += PropertyName->getName().str();
std::string NameWithSuffix = PropertyName->getName().str();
NameWithSuffix += '_';
for(; Class; Class = Class->getSuperClass()) {
// FIXME: We could screen the type of each ivar for compatibility with
// the property, but is that being too paternal?
for (ObjCInterfaceDecl::ivar_iterator IVar = Class->ivar_begin(),
IVarEnd = Class->ivar_end();
IVar != IVarEnd; ++IVar)
Results.AddResult(Result(*IVar, 0), CurContext, 0, false);
for (ObjCIvarDecl *Ivar = Class->all_declared_ivar_begin(); Ivar;
Ivar = Ivar->getNextIvar()) {
// Determine whether we've seen an ivar with a name similar to the
// property.
if (!SawSimilarlyNamedIvar &&
(PropertyName->getName() == Ivar->getName() ||
NameWithPrefix == Ivar->getName() ||
NameWithSuffix == Ivar->getName()))
SawSimilarlyNamedIvar = true;
Results.AddResult(Result(Ivar, 0), CurContext, 0, false);
}
}
if (!SawSimilarlyNamedIvar) {
// Create ivar result _propName, that the user can use to synthesize
// an ivar of the appropriate type.
QualType T = Context.getObjCIdType();
if (Class) {
if (ObjCPropertyDecl *Property
= Class->FindPropertyDeclaration(PropertyName))
T = Property->getType().getNonReferenceType().getUnqualifiedType();
}
unsigned Priority = CCP_MemberDeclaration;
typedef CodeCompletionResult Result;
CodeCompletionAllocator &Allocator = Results.getAllocator();
CodeCompletionBuilder Builder(Allocator, Priority,CXAvailability_Available);
Builder.AddResultTypeChunk(GetCompletionTypeString(T, Context, Allocator));
Builder.AddTypedTextChunk(Allocator.CopyString(NameWithPrefix));
Results.AddResult(Result(Builder.TakeString(), Priority,
CXCursor_ObjCIvarDecl));
}
Results.ExitScope();
HandleCodeCompleteResults(this, CodeCompleter,

View File

@@ -41,8 +41,10 @@ id test(I3 *i3) {
// CHECK-CC2-NEXT: ObjCPropertyDecl:{ResultType id}{TypedText Prop3}
// CHECK-CC2: ObjCPropertyDecl:{ResultType id}{TypedText Prop4}
// RUN: c-index-test -code-completion-at=%s:20:35 %s | FileCheck -check-prefix=CHECK-CC3 %s
// CHECK-CC3: ObjCIvarDecl:{ResultType int}{TypedText RandomIVar}
// CHECK-CC3: ObjCIvarDecl:{ResultType id}{TypedText StoredProp3}
// CHECK-CC3: ObjCIvarDecl:{ResultType id}{TypedText _Prop3} (35)
// CHECK-CC3: ObjCIvarDecl:{ResultType int}{TypedText RandomIVar} (35)
// CHECK-CC3: ObjCIvarDecl:{ResultType id}{TypedText StoredProp3} (35)
// RUN: c-index-test -code-completion-at=%s:21:10 %s | FileCheck -check-prefix=CHECK-CC4 %s
// CHECK-CC4: ObjCPropertyDecl:{ResultType int}{TypedText Prop0}
// CHECK-CC4-NEXT: ObjCPropertyDecl:{ResultType id}{TypedText Prop4}