mirror of
https://github.com/RGBCube/serenity
synced 2025-07-24 15:57:35 +00:00
HackStudio+CppLanguageServer: Remove lexer-based autocomplete engine
The parser-based autocomplete engine is at a point where it's stable enough that I don't think there's a need for the lexer-based alternative anymore.
This commit is contained in:
parent
ddb278ab85
commit
b1531b78f6
11 changed files with 0 additions and 156 deletions
|
@ -898,8 +898,6 @@ void HackStudioWidget::create_project_menubar(GUI::Menubar& menubar)
|
||||||
auto& project_menu = menubar.add_menu("&Project");
|
auto& project_menu = menubar.add_menu("&Project");
|
||||||
project_menu.add_action(*m_new_file_action);
|
project_menu.add_action(*m_new_file_action);
|
||||||
project_menu.add_action(*m_new_directory_action);
|
project_menu.add_action(*m_new_directory_action);
|
||||||
project_menu.add_separator();
|
|
||||||
project_menu.add_action(*create_set_autocomplete_mode_action());
|
|
||||||
}
|
}
|
||||||
|
|
||||||
void HackStudioWidget::create_edit_menubar(GUI::Menubar& menubar)
|
void HackStudioWidget::create_edit_menubar(GUI::Menubar& menubar)
|
||||||
|
@ -1000,15 +998,6 @@ NonnullRefPtr<GUI::Action> HackStudioWidget::create_stop_action()
|
||||||
return action;
|
return action;
|
||||||
}
|
}
|
||||||
|
|
||||||
NonnullRefPtr<GUI::Action> HackStudioWidget::create_set_autocomplete_mode_action()
|
|
||||||
{
|
|
||||||
auto action = GUI::Action::create_checkable("AutoComplete C++ with &Parser", [this](auto& action) {
|
|
||||||
get_language_client<LanguageClients::Cpp::ServerConnection>(project().root_path())->set_autocomplete_mode(action.is_checked() ? "Parser" : "Lexer");
|
|
||||||
});
|
|
||||||
action->set_checked(true);
|
|
||||||
return action;
|
|
||||||
}
|
|
||||||
|
|
||||||
void HackStudioWidget::initialize_menubar(GUI::Menubar& menubar)
|
void HackStudioWidget::initialize_menubar(GUI::Menubar& menubar)
|
||||||
{
|
{
|
||||||
create_file_menubar(menubar);
|
create_file_menubar(menubar);
|
||||||
|
|
|
@ -88,7 +88,6 @@ private:
|
||||||
NonnullRefPtr<GUI::Action> create_build_action();
|
NonnullRefPtr<GUI::Action> create_build_action();
|
||||||
NonnullRefPtr<GUI::Action> create_run_action();
|
NonnullRefPtr<GUI::Action> create_run_action();
|
||||||
NonnullRefPtr<GUI::Action> create_stop_action();
|
NonnullRefPtr<GUI::Action> create_stop_action();
|
||||||
NonnullRefPtr<GUI::Action> create_set_autocomplete_mode_action();
|
|
||||||
|
|
||||||
void add_new_editor(GUI::Widget& parent);
|
void add_new_editor(GUI::Widget& parent);
|
||||||
RefPtr<EditorWrapper> get_editor_of_file(const String& filename);
|
RefPtr<EditorWrapper> get_editor_of_file(const String& filename);
|
||||||
|
|
|
@ -84,13 +84,6 @@ void LanguageClient::provide_autocomplete_suggestions(const Vector<GUI::Autocomp
|
||||||
// Otherwise, drop it on the floor :shrug:
|
// Otherwise, drop it on the floor :shrug:
|
||||||
}
|
}
|
||||||
|
|
||||||
void LanguageClient::set_autocomplete_mode(const String& mode)
|
|
||||||
{
|
|
||||||
if (!m_connection_wrapper.connection())
|
|
||||||
return;
|
|
||||||
m_connection_wrapper.connection()->async_set_auto_complete_mode(mode);
|
|
||||||
}
|
|
||||||
|
|
||||||
void LanguageClient::set_active_client()
|
void LanguageClient::set_active_client()
|
||||||
{
|
{
|
||||||
if (!m_connection_wrapper.connection())
|
if (!m_connection_wrapper.connection())
|
||||||
|
|
|
@ -128,7 +128,6 @@ public:
|
||||||
virtual void insert_text(const String& path, const String& text, size_t line, size_t column);
|
virtual void insert_text(const String& path, const String& text, size_t line, size_t column);
|
||||||
virtual void remove_text(const String& path, size_t from_line, size_t from_column, size_t to_line, size_t to_column);
|
virtual void remove_text(const String& path, size_t from_line, size_t from_column, size_t to_line, size_t to_column);
|
||||||
virtual void request_autocomplete(const String& path, size_t cursor_line, size_t cursor_column);
|
virtual void request_autocomplete(const String& path, size_t cursor_line, size_t cursor_column);
|
||||||
virtual void set_autocomplete_mode(const String& mode);
|
|
||||||
virtual void search_declaration(const String& path, size_t line, size_t column);
|
virtual void search_declaration(const String& path, size_t line, size_t column);
|
||||||
|
|
||||||
void provide_autocomplete_suggestions(const Vector<GUI::AutocompleteProvider::Entry>&) const;
|
void provide_autocomplete_suggestions(const Vector<GUI::AutocompleteProvider::Entry>&) const;
|
||||||
|
|
|
@ -34,7 +34,6 @@ protected:
|
||||||
virtual void set_file_content(String const&, String const&) override;
|
virtual void set_file_content(String const&, String const&) override;
|
||||||
virtual void auto_complete_suggestions(GUI::AutocompleteProvider::ProjectLocation const&) override;
|
virtual void auto_complete_suggestions(GUI::AutocompleteProvider::ProjectLocation const&) override;
|
||||||
virtual void find_declaration(GUI::AutocompleteProvider::ProjectLocation const&) override;
|
virtual void find_declaration(GUI::AutocompleteProvider::ProjectLocation const&) override;
|
||||||
virtual void set_auto_complete_mode(String const&) override = 0;
|
|
||||||
|
|
||||||
FileDB m_filedb;
|
FileDB m_filedb;
|
||||||
OwnPtr<AutoCompleteEngine> m_autocomplete_engine;
|
OwnPtr<AutoCompleteEngine> m_autocomplete_engine;
|
||||||
|
|
|
@ -1,5 +1,4 @@
|
||||||
set(SOURCES
|
set(SOURCES
|
||||||
LexerAutoComplete.cpp
|
|
||||||
ParserAutoComplete.cpp
|
ParserAutoComplete.cpp
|
||||||
Tests.cpp
|
Tests.cpp
|
||||||
main.cpp
|
main.cpp
|
||||||
|
|
|
@ -6,7 +6,6 @@
|
||||||
|
|
||||||
#pragma once
|
#pragma once
|
||||||
|
|
||||||
#include "LexerAutoComplete.h"
|
|
||||||
#include "ParserAutoComplete.h"
|
#include "ParserAutoComplete.h"
|
||||||
#include <DevTools/HackStudio/LanguageServers/ClientConnection.h>
|
#include <DevTools/HackStudio/LanguageServers/ClientConnection.h>
|
||||||
|
|
||||||
|
@ -26,15 +25,5 @@ public:
|
||||||
}
|
}
|
||||||
|
|
||||||
virtual ~ClientConnection() override = default;
|
virtual ~ClientConnection() override = default;
|
||||||
|
|
||||||
private:
|
|
||||||
virtual void set_auto_complete_mode(String const& mode) override
|
|
||||||
{
|
|
||||||
dbgln_if(CPP_LANGUAGE_SERVER_DEBUG, "SetAutoCompleteMode: {}", mode);
|
|
||||||
if (mode == "Parser")
|
|
||||||
m_autocomplete_engine = make<ParserAutoComplete>(m_filedb);
|
|
||||||
else
|
|
||||||
m_autocomplete_engine = make<LexerAutoComplete>(m_filedb);
|
|
||||||
}
|
|
||||||
};
|
};
|
||||||
}
|
}
|
||||||
|
|
|
@ -1,87 +0,0 @@
|
||||||
/*
|
|
||||||
* Copyright (c) 2020, Itamar S. <itamar8910@gmail.com>
|
|
||||||
*
|
|
||||||
* SPDX-License-Identifier: BSD-2-Clause
|
|
||||||
*/
|
|
||||||
|
|
||||||
#include "LexerAutoComplete.h"
|
|
||||||
#include <AK/Debug.h>
|
|
||||||
#include <AK/HashTable.h>
|
|
||||||
#include <LibCpp/Lexer.h>
|
|
||||||
|
|
||||||
namespace LanguageServers::Cpp {
|
|
||||||
|
|
||||||
LexerAutoComplete::LexerAutoComplete(const FileDB& filedb)
|
|
||||||
: AutoCompleteEngine(filedb)
|
|
||||||
{
|
|
||||||
}
|
|
||||||
|
|
||||||
Vector<GUI::AutocompleteProvider::Entry> LexerAutoComplete::get_suggestions(const String& file, const GUI::TextPosition& autocomplete_position)
|
|
||||||
{
|
|
||||||
auto document = filedb().get(file);
|
|
||||||
if (!document) {
|
|
||||||
dbgln("didn't find document for {}", file);
|
|
||||||
return {};
|
|
||||||
}
|
|
||||||
auto code = document->text();
|
|
||||||
auto lines = code.split('\n', true);
|
|
||||||
Cpp::Lexer lexer(code);
|
|
||||||
auto tokens = lexer.lex();
|
|
||||||
|
|
||||||
auto index_of_target_token = token_in_position(tokens, autocomplete_position);
|
|
||||||
if (!index_of_target_token.has_value())
|
|
||||||
return {};
|
|
||||||
|
|
||||||
auto suggestions = identifier_prefixes(lines, tokens, index_of_target_token.value());
|
|
||||||
|
|
||||||
if constexpr (AUTOCOMPLETE_DEBUG) {
|
|
||||||
for (auto& suggestion : suggestions) {
|
|
||||||
dbgln("suggestion: {}", suggestion.completion);
|
|
||||||
}
|
|
||||||
}
|
|
||||||
|
|
||||||
return suggestions;
|
|
||||||
}
|
|
||||||
|
|
||||||
StringView LexerAutoComplete::text_of_token(const Vector<String>& lines, const Cpp::Token& token)
|
|
||||||
{
|
|
||||||
VERIFY(token.start().line == token.end().line);
|
|
||||||
VERIFY(token.start().column <= token.end().column);
|
|
||||||
return lines[token.start().line].substring_view(token.start().column, token.end().column - token.start().column + 1);
|
|
||||||
}
|
|
||||||
|
|
||||||
Optional<size_t> LexerAutoComplete::token_in_position(const Vector<Cpp::Token>& tokens, const GUI::TextPosition& position)
|
|
||||||
{
|
|
||||||
for (size_t token_index = 0; token_index < tokens.size(); ++token_index) {
|
|
||||||
auto& token = tokens[token_index];
|
|
||||||
if (token.start().line != token.end().line)
|
|
||||||
continue;
|
|
||||||
if (token.start().line != position.line())
|
|
||||||
continue;
|
|
||||||
if (token.start().column + 1 > position.column() || token.end().column + 1 < position.column())
|
|
||||||
continue;
|
|
||||||
return token_index;
|
|
||||||
}
|
|
||||||
return {};
|
|
||||||
}
|
|
||||||
|
|
||||||
Vector<GUI::AutocompleteProvider::Entry> LexerAutoComplete::identifier_prefixes(const Vector<String>& lines, const Vector<Cpp::Token>& tokens, size_t target_token_index)
|
|
||||||
{
|
|
||||||
auto partial_input = text_of_token(lines, tokens[target_token_index]);
|
|
||||||
Vector<GUI::AutocompleteProvider::Entry> suggestions;
|
|
||||||
|
|
||||||
HashTable<String> suggestions_lookup; // To avoid duplicate results
|
|
||||||
|
|
||||||
for (size_t i = 0; i < target_token_index; ++i) {
|
|
||||||
auto& token = tokens[i];
|
|
||||||
if (token.type() != Cpp::Token::Type::Identifier)
|
|
||||||
continue;
|
|
||||||
auto text = text_of_token(lines, token);
|
|
||||||
if (text.starts_with(partial_input) && suggestions_lookup.set(text) == AK::HashSetResult::InsertedNewEntry) {
|
|
||||||
suggestions.append({ text, partial_input.length(), GUI::AutocompleteProvider::CompletionKind::Identifier });
|
|
||||||
}
|
|
||||||
}
|
|
||||||
return suggestions;
|
|
||||||
}
|
|
||||||
|
|
||||||
}
|
|
|
@ -1,32 +0,0 @@
|
||||||
/*
|
|
||||||
* Copyright (c) 2020, Itamar S. <itamar8910@gmail.com>
|
|
||||||
*
|
|
||||||
* SPDX-License-Identifier: BSD-2-Clause
|
|
||||||
*/
|
|
||||||
|
|
||||||
#pragma once
|
|
||||||
|
|
||||||
#include <AK/String.h>
|
|
||||||
#include <AK/Vector.h>
|
|
||||||
#include <DevTools/HackStudio/AutoCompleteResponse.h>
|
|
||||||
#include <DevTools/HackStudio/LanguageServers/AutoCompleteEngine.h>
|
|
||||||
#include <LibCpp/Lexer.h>
|
|
||||||
#include <LibGUI/TextPosition.h>
|
|
||||||
|
|
||||||
namespace LanguageServers::Cpp {
|
|
||||||
|
|
||||||
using namespace ::Cpp;
|
|
||||||
|
|
||||||
class LexerAutoComplete : public AutoCompleteEngine {
|
|
||||||
public:
|
|
||||||
LexerAutoComplete(const FileDB& filedb);
|
|
||||||
|
|
||||||
virtual Vector<GUI::AutocompleteProvider::Entry> get_suggestions(const String& file, const GUI::TextPosition& autocomplete_position) override;
|
|
||||||
|
|
||||||
private:
|
|
||||||
Optional<size_t> token_in_position(const Vector<Cpp::Token>&, const GUI::TextPosition&);
|
|
||||||
StringView text_of_token(const Vector<String>& lines, const Cpp::Token&);
|
|
||||||
Vector<GUI::AutocompleteProvider::Entry> identifier_prefixes(const Vector<String>& lines, const Vector<Cpp::Token>&, size_t target_token_index);
|
|
||||||
};
|
|
||||||
|
|
||||||
}
|
|
|
@ -8,6 +8,5 @@ endpoint LanguageServer
|
||||||
set_file_content(String filename, String content) =|
|
set_file_content(String filename, String content) =|
|
||||||
|
|
||||||
auto_complete_suggestions(GUI::AutocompleteProvider::ProjectLocation location) =|
|
auto_complete_suggestions(GUI::AutocompleteProvider::ProjectLocation location) =|
|
||||||
set_auto_complete_mode(String mode) =|
|
|
||||||
find_declaration(GUI::AutocompleteProvider::ProjectLocation location) =|
|
find_declaration(GUI::AutocompleteProvider::ProjectLocation location) =|
|
||||||
}
|
}
|
||||||
|
|
|
@ -23,8 +23,5 @@ class ClientConnection final : public LanguageServers::ClientConnection {
|
||||||
};
|
};
|
||||||
}
|
}
|
||||||
virtual ~ClientConnection() override = default;
|
virtual ~ClientConnection() override = default;
|
||||||
|
|
||||||
private:
|
|
||||||
virtual void set_auto_complete_mode(String const&) override { }
|
|
||||||
};
|
};
|
||||||
}
|
}
|
||||||
|
|
Loading…
Add table
Add a link
Reference in a new issue