mirror of
https://github.com/MaskRay/ccls.git
synced 2025-01-19 12:05:50 +00:00
[indexer] Make hover
optional (#176)
On textDocument/hover requests, return `detailed_name` if `hover` is unavailable Don't include leading `type_name` in `detailed_name` for CXIdxEntityEnumConstant, i.e. `Foo Foo::a` -> `Foo::a`
This commit is contained in:
parent
ba4a5e91cb
commit
c3c0feecb2
@ -61,6 +61,9 @@ bool IsLocalSemanticContainer(CXCursorKind kind) {
|
||||
case CXCursor_UnionDecl:
|
||||
case CXCursor_ClassDecl:
|
||||
case CXCursor_EnumDecl:
|
||||
// TODO Add more Objective-C containers
|
||||
case CXCursor_ObjCInterfaceDecl:
|
||||
case CXCursor_ObjCImplementationDecl:
|
||||
return false;
|
||||
default:
|
||||
return true;
|
||||
@ -87,7 +90,8 @@ struct NamespaceHelper {
|
||||
ClangCursor cursor = container->cursor;
|
||||
std::vector<ClangCursor> namespaces;
|
||||
std::string qualifier;
|
||||
while (cursor.get_kind() != CXCursor_TranslationUnit) {
|
||||
while (cursor.get_kind() != CXCursor_TranslationUnit &&
|
||||
!IsLocalSemanticContainer(cursor.get_kind())) {
|
||||
auto it = container_cursor_to_qualified_name.find(cursor);
|
||||
if (it != container_cursor_to_qualified_name.end()) {
|
||||
qualifier = it->second;
|
||||
@ -99,6 +103,8 @@ struct NamespaceHelper {
|
||||
for (size_t i = namespaces.size(); i > 0; ) {
|
||||
i--;
|
||||
std::string name = namespaces[i].get_spelling();
|
||||
// Empty name indicates unnamed namespace, anonymous struct, anonymous
|
||||
// union, ...
|
||||
qualifier += name.empty() ? "(anon)" : name;
|
||||
qualifier += "::";
|
||||
container_cursor_to_qualified_name[namespaces[i]] = qualifier;
|
||||
@ -1031,10 +1037,14 @@ void OnIndexDeclaration(CXClientData client_data, const CXIdxDeclInfo* decl) {
|
||||
if (type_name.find("(lambda at") != std::string::npos)
|
||||
type_name = "lambda";
|
||||
|
||||
var->def.detailed_name =
|
||||
type_name + " " +
|
||||
{
|
||||
std::string qualified_name =
|
||||
ns->QualifiedName(decl->semanticContainer, var->def.short_name);
|
||||
var->def.hover = type_name;
|
||||
if (decl->entityInfo->kind == CXIdxEntity_EnumConstant)
|
||||
var->def.detailed_name = std::move(qualified_name);
|
||||
else
|
||||
var->def.detailed_name = type_name + " " + std::move(qualified_name);
|
||||
}
|
||||
|
||||
var->def.is_local =
|
||||
!decl->semanticContainer ||
|
||||
@ -1258,11 +1268,10 @@ void OnIndexDeclaration(CXClientData client_data, const CXIdxDeclInfo* decl) {
|
||||
type->def.detailed_name =
|
||||
ns->QualifiedName(decl->semanticContainer, type->def.short_name);
|
||||
|
||||
type->def.hover = type->def.detailed_name;
|
||||
|
||||
// For Typedef/CXXTypeAlias spanning a few lines, display the declaration line,
|
||||
// with spelling name replaced with qualified name.
|
||||
// TODO Think how to display multi-line declaration like `typedef struct { ... } foo;`
|
||||
// https://github.com/jacobdufault/cquery/issues/29
|
||||
if (extent.end.line - extent.start.line <
|
||||
kMaxLinesDisplayTypeAliasDeclarations) {
|
||||
FileContentsWithOffsets& fc = param->file_contents[db->path];
|
||||
@ -1312,7 +1321,6 @@ void OnIndexDeclaration(CXClientData client_data, const CXIdxDeclInfo* decl) {
|
||||
|
||||
type->def.detailed_name =
|
||||
ns->QualifiedName(decl->semanticContainer, type->def.short_name);
|
||||
type->def.hover = type->def.detailed_name;
|
||||
// }
|
||||
|
||||
if (decl->isDefinition) {
|
||||
@ -1445,7 +1453,6 @@ void OnIndexReference(CXClientData client_data, const CXIdxEntityRefInfo* ref) {
|
||||
std::string type_name = ToString(
|
||||
clang_getTypeSpelling(clang_getCursorType(referenced.cx_cursor)));
|
||||
var->def.detailed_name = type_name + " " + var->def.short_name;
|
||||
var->def.hover = type_name;
|
||||
var->def.is_local = false;
|
||||
UniqueAdd(var->uses, ResolveSpelling(referenced.cx_cursor));
|
||||
AddDeclInitializerUsages(db, referenced.cx_cursor);
|
||||
|
@ -149,7 +149,7 @@ struct TypeDefDefinitionData {
|
||||
// General metadata.
|
||||
std::string short_name;
|
||||
std::string detailed_name;
|
||||
std::string hover;
|
||||
optional<std::string> hover;
|
||||
|
||||
// While a class/type can technically have a separate declaration/definition,
|
||||
// it doesn't really happen in practice. The declaration never contains
|
||||
@ -247,7 +247,7 @@ struct FuncDefDefinitionData {
|
||||
// General metadata.
|
||||
std::string short_name;
|
||||
std::string detailed_name;
|
||||
std::string hover;
|
||||
optional<std::string> hover;
|
||||
optional<Range> definition_spelling;
|
||||
optional<Range> definition_extent;
|
||||
|
||||
@ -362,7 +362,7 @@ struct VarDefDefinitionData {
|
||||
// General metadata.
|
||||
std::string short_name;
|
||||
std::string detailed_name;
|
||||
std::string hover;
|
||||
optional<std::string> hover;
|
||||
optional<Range> declaration;
|
||||
// TODO: definitions should be a list of ranges, since there can be more
|
||||
// than one - when??
|
||||
|
@ -7,20 +7,29 @@ std::string GetHoverForSymbol(QueryDatabase* db, const SymbolIdx& symbol) {
|
||||
switch (symbol.kind) {
|
||||
case SymbolKind::Type: {
|
||||
QueryType& type = db->types[symbol.idx];
|
||||
if (type.def)
|
||||
return type.def->hover;
|
||||
if (type.def) {
|
||||
if (type.def->hover)
|
||||
return *type.def->hover;
|
||||
return type.def->detailed_name;
|
||||
}
|
||||
break;
|
||||
}
|
||||
case SymbolKind::Func: {
|
||||
QueryFunc& func = db->funcs[symbol.idx];
|
||||
if (func.def)
|
||||
return func.def->hover;
|
||||
if (func.def) {
|
||||
if (func.def->hover)
|
||||
return *func.def->hover;
|
||||
return func.def->detailed_name;
|
||||
}
|
||||
break;
|
||||
}
|
||||
case SymbolKind::Var: {
|
||||
QueryVar& var = db->vars[symbol.idx];
|
||||
if (var.def)
|
||||
return var.def->hover;
|
||||
if (var.def) {
|
||||
if (var.def->hover)
|
||||
return *var.def->hover;
|
||||
return var.def->detailed_name;
|
||||
}
|
||||
break;
|
||||
}
|
||||
case SymbolKind::File:
|
||||
|
Loading…
Reference in New Issue
Block a user